scanf return values

This is a discussion on scanf return values within the C Programming forums, part of the General Programming Boards category; hi guys, ok, i just realised something about scanf and its return values. when a user tries to assign (for ...

  1. #1
    Registered User
    Join Date
    Sep 2009
    Posts
    10

    Question scanf return values

    hi guys,

    ok, i just realised something about scanf and its return values. when a user tries to assign (for example) three values to three variables, the return value of scanf is 3. nice.
    THEN, if the user decides to input 4 values, return value of scanf is still three (since it reads only first three of them). where has the fourth value gone?
    I'd like the user to be forced to input just three numbers by using:
    Code:
    if ((scanf("%lf%lf%i", &num1, &num2, &num3)) == 3)
    {
           //some more of these calculations
    }
    
    else
    {
          printf("Wrong number of arguments\n");
          return 1;
    }
    but that does not work. if i give 4 values, programme gives no errors and carries on with calculations.

    how would i restrict user to input only 3 values otherwise? is that a normal behavior for scanf?

  2. #2
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    21,758
    Quote Originally Posted by pirog
    THEN, if the user decides to input 4 values, return value of scanf is still three (since it reads only first three of them). where has the fourth value gone?
    The fourth value remains in the input buffer.

    Quote Originally Posted by pirog
    how would i restrict user to input only 3 values otherwise?
    You could read in the whole line and parse it using say, sscanf().
    C + C++ Compiler: MinGW port of GCC
    Version Control System: Bazaar

    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  3. #3
    Registered User
    Join Date
    Sep 2009
    Posts
    10
    Thanks laselight,

    i think it is an unnecessary use of input buffer. do extra values keep on filling up buffer and can this buffer overflow (if the number given to it is too large, for example)?

    hmmm, reading the line and then parsing through sscanf()? i thought scanf() would do a similar job without the need of scanning the whole input line. well, I am not even a moderate (yet) programmer myself, but I'll try your solution.

    yet, what bugs me, is that scanf can only give me first three values and not the actual number of values i provided. Makes IF statement redundant! heh.

    thanks anyway.

  4. #4
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    21,758
    Quote Originally Posted by pirog
    yet, what bugs me, is that scanf can only give me first three values and not the actual number of values i provided. Makes IF statement redundant! heh.
    What happens if the user only enters two values?
    C + C++ Compiler: MinGW port of GCC
    Version Control System: Bazaar

    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  5. #5
    Registered User
    Join Date
    Sep 2009
    Posts
    10
    laserlight,

    actually, the programme waits until i enter at least 3 values. even if i separate them by X number of CARRIAGE RETURNS. Of course the programme (however small) terminates on the account of any letters. i guess that's typical of SCANF().

  6. #6
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    21,758
    To enter just two values, enter them, then simulate EOF (e.g., CTRL + Z or CTRL + D).
    C + C++ Compiler: MinGW port of GCC
    Version Control System: Bazaar

    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  7. #7
    Registered User
    Join Date
    Sep 2009
    Posts
    10
    while running this programme in the terminal and pressing C-Z or C-D gives me russian letters (my keyboard is set to Eng/Rus). Anyway, the following ensures such termination and gives my own error message:
    Code:
    	if (n != EOF)
    		printf("Warning: Input reading terminated by error.\n");
    where n is my SCANF() return value
    but i am not worried about the user inputting only two values (the above takes care of that). it is him putting 4 values, that still results in return value of SCANF() to be 3. I think it is a shame for scanf to take on predetermined number of arguments.

    i am still to implement your solution involving SSCANF() - doing somehting else at the moment.

  8. #8
    Registered User
    Join Date
    Sep 2009
    Posts
    10
    Tried to implement the SSCANF suggestion, but unsuccessfully.
    From what errors I could unscramble, the issue was in an incorrect formating. I am going to stick to SCANF routine, although I still think it is not so beautiful.

    thanks for help anyway

  9. #9
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,046
    You can't just use sscanf() as a drop-in replacement for scanf(). sscanf() parses its tokens from a char[] array rather than from stdin. So the general idea is that you use fgets() or a similar function to read data into a buffer, and then use sscanf() to parse that buffer. Quick example:
    Code:
    #include <stdio.h>
    
    int main() {
        char buffer[BUFSIZ];
        int x, y, z;
        
        printf("Enter exactly three numbers on one line:\n");
        for(;;) {
            int bogus;
            
            if(!fgets(buffer, sizeof buffer, stdin)) return 1;
            
            if(sscanf(buffer, "%d%d%d%d", &x, &y, &z, &bogus) != 3) {
                printf("Hey. I said *exactly* three numbers.\n");
            }
            else break;
        }
        
        printf("Product %d*%d*%d = %d\n", x, y, z, x*y*z);
        
        return 0;
    }
    Example run:
    Code:
    Enter exactly three numbers on one line:
    1 2
    Hey. I said *exactly* three numbers.
    1 2 3 4
    Hey. I said *exactly* three numbers.
    1 2 3
    Product 1*2*3 = 6
    There are other ways to see if the user entered data beyond what you expected. You could use %p to see how far sscanf() read and then see if there were any non-space characters between there and the end of the string (or just use %c to make your life a lot easier).
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

  10. #10
    Registered User
    Join Date
    Sep 2009
    Posts
    10
    Thanks for such an informative reply, DWKS!!!

    I shall certainly try it your way, but as far as i can see that pretty much answers my question.
    What i was doing, as you probably understood from previous posts, was using SSCANF just as I would use SCANF. Of course, I couldn't make getc to work either and was left to use scanf's buffer and that basically defeats the purpose of SSCANF.

    Thanks a lot. I'll keep you posted on my progress.

  11. #11
    Registered User
    Join Date
    Sep 2009
    Posts
    10
    dwks,

    the example you've given worked like a charm. Although i did not get the idea behind bogus variable, but then it came to me that it is a dummy variable and is necessary for the limitation of user input.
    Couldn't define BUFFSIZE in pre-processor and then use it in CHAR BUFF[BUFFSIZE], so i just set it in declaration CHAR BUFF[120]. Other than that, there were no probs with the example.

    Only thing left is to apply the solution to my programme.

    Thanks a lot!

  12. #12
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,046
    Although i did not get the idea behind bogus variable, but then it came to me that it is a dummy variable and is necessary for the limitation of user input.
    Yes, "dummy" would perhaps have been a better name. Oh well.

    Couldn't define BUFFSIZE in pre-processor and then use it in CHAR BUFF[BUFFSIZE], so i just set it in declaration CHAR BUFF[120]. Other than that, there were no probs with the example.
    BUFSIZ is pre-defined in stdio.h to be something at least 512. It's a good size to use for buffers. If you want to use your own size, of course, you could say #define BUFFER_SIZE 120 or something -- but don't try to re-define BUFSIZ, since the compiler probably won't like that too much.
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

  13. #13
    Registered User
    Join Date
    Sep 2009
    Posts
    10
    hey dwks,

    i defined BUFFSIZE in a pre-processor statement as you have it in your last post, but my compiler did not like it. not quite sure why (i might have a look at it later), but that's the reason i defined it in declaration of CHAR BUFF[120]

    i took a liberty of looking at your webpage, it looks good - i might visit it for reference purposes

    good luck

    p.s. still, i am left to implement your solution in my programme (when i get a chance)

  14. #14
    and the Hat of Guessing tabstop's Avatar
    Join Date
    Nov 2007
    Posts
    14,185
    Quote Originally Posted by pirog View Post
    hey dwks,

    i defined BUFFSIZE in a pre-processor statement as you have it in your last post, but my compiler did not like it. not quite sure why (i might have a look at it later), but that's the reason i defined it in declaration of CHAR BUFF[120]

    i took a liberty of looking at your webpage, it looks good - i might visit it for reference purposes

    good luck

    p.s. still, i am left to implement your solution in my programme (when i get a chance)
    I like guessing: don't put a semicolon at the end of your define (and don't put an equals sign in it either).

  15. #15
    Registered User
    Join Date
    Sep 2009
    Posts
    10
    hey tabstop,

    i did not keep the backup of it (since that was a trial file, although i do in general) but i did not use the equal sign.
    Yet, I am pretty sure i had a semicolon in there

    appreciated!
    thanks to everyone for their input.

Page 1 of 2 12 LastLast
Popular pages Recent additions subscribe to a feed

Similar Threads

  1. How can I make this code more elegant?
    By ejohns85 in forum C++ Programming
    Replies: 3
    Last Post: 04-02-2009, 08:55 AM
  2. DirectInput help
    By Muphin in forum Game Programming
    Replies: 2
    Last Post: 09-10-2005, 11:52 AM
  3. Pong is completed!!!
    By Shamino in forum Game Programming
    Replies: 11
    Last Post: 05-26-2005, 10:50 AM
  4. problem with open gl engine.
    By gell10 in forum Game Programming
    Replies: 1
    Last Post: 08-21-2003, 04:10 AM
  5. Algorithm to walk through a maze.
    By Nutshell in forum C Programming
    Replies: 30
    Last Post: 01-21-2002, 12:54 AM

Tags for this Thread


1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21