Thread: QUestion on gets

  1. #1
    Registered User
    Join Date
    Sep 2008
    Posts
    54

    Question QUestion on gets

    Ok had this question from my friend. basically he's scanning info from keyboard to an array of structures. But here's the thing, he started using scanf which works fine but then there is a scenario that imagine the address has a space between, so he used gets for that section. However, now the program compiles but when it reaches that section it skips that area and goes to the next section. Whats the problem there?


    printf("\nEnter First Name A Customer: " );
    scanf("%s", data[i].fname ); /* Read the horse's name */
    printf("\nEnter %s's Last Name: ", data[i].fname );
    scanf("%s", data[i].lname );
    printf("\nEnter %s's Street Address: ", data[i].fname );
    gets(data[i].staddress);
    printf("\nEnter Country Location of %s: ", data[i].fname );
    scanf("%s",data[i].country );

    however, if you use scanf it works good, but the gets is skipped. how can it be fixed.

  2. #2
    Banned master5001's Avatar
    Join Date
    Aug 2001
    Location
    Visalia, CA, USA
    Posts
    3,685
    Don't even use gets(). Use fgets().

  3. #3
    Registered User
    Join Date
    Sep 2008
    Posts
    54
    Quote Originally Posted by master5001 View Post
    Don't even use gets(). Use fgets().
    Well i did try fgets like this fgets(data[i].staddress,sizeof(data[i].staddress),stdin); but i still got the same result as using gets

  4. #4
    Banned master5001's Avatar
    Join Date
    Aug 2001
    Location
    Visalia, CA, USA
    Posts
    3,685
    I wasn't even trying to answer your question. Just fix something dubious in your code. Is it perhaps possible that scanf() is your problem? I.e. it is not pulling in the input the way you desire.

  5. #5
    Registered User
    Join Date
    Sep 2008
    Posts
    54
    Quote Originally Posted by master5001 View Post
    I wasn't even trying to answer your question. Just fix something dubious in your code. Is it perhaps possible that scanf() is your problem? I.e. it is not pulling in the input the way you desire.
    lol, ok. Well matt its on the gets, when running the program it simply skips the gets, and i got no idea why, it goes to the next scanf that follows.

  6. #6
    Banned master5001's Avatar
    Join Date
    Aug 2001
    Location
    Visalia, CA, USA
    Posts
    3,685
    Check it out though, if you have scanf() leave crap in the input stream, you may end up having your subsequent call to fgets() not work as planned. To fight this you could always call fgets() and use sscanf() to read from the line that you read in with fgets().

    Also, and kind of unrelated but still important: Your scanf("%s", variable) lines are prone to buffer overflow. You should do something like scanf("%10s", variable) or whatever sizeof variable happens to equal.

  7. #7
    Registered User
    Join Date
    Sep 2008
    Posts
    54
    Quote Originally Posted by master5001 View Post
    Check it out though, if you have scanf() leave crap in the input stream, you may end up having your subsequent call to fgets() not work as planned. To fight this you could always call fgets() and use sscanf() to read from the line that you read in with fgets().

    Also, and kind of unrelated but still important: Your scanf("%s", variable) lines are prone to buffer overflow. You should do something like scanf("%10s", variable) or whatever sizeof variable happens to equal.
    thank you, yes the buffer had trash, used fflush() to clear out the contents, got it working, we can call this closed now, thanks Matt,Aria said ud help, lol

  8. #8
    Banned master5001's Avatar
    Join Date
    Aug 2001
    Location
    Visalia, CA, USA
    Posts
    3,685
    Yeah no problem.

    Using fflush() on stdin is actually undefined according to the standard. If you want to do it the right way I would do it like this:

    Example:
    Code:
    char line[4096]; /* 4k is a large enough line, methinks */
    
    printf("\nEnter First Name A Customer: " );
    fgets(line, sizeof line, stdin);
    sscanf(line, "%s", data[i].fname ); /* Read the horse's name */
    printf("\nEnter %s's Last Name: ", data[i].fname );
    fgets(line, sizeof line, stdin);
    sscanf("%s", data[i].lname );
    printf("\nEnter %s's Street Address: ", data[i].fname );
    fgets(data[i].staddress, sizeof data[i].staddress, stdin);
    printf("\nEnter Country Location of %s: ", data[i].fname );
    fgets(line, sizeof line, stdin);
    sscanf("%s",data[i].country );
    Last edited by master5001; 11-03-2008 at 05:28 PM.

  9. #9
    C++まいる!Cをこわせ!
    Join Date
    Oct 2007
    Location
    Inside my computer
    Posts
    24,654
    Tsch, you know as well as I that that code is no better than the original.
    There are several examples to get rid of the trailing newline, and sscanf is probably the worst of those alternatives, especially when buffer sizes go unspecified.
    Quote Originally Posted by Adak View Post
    io.h certainly IS included in some modern compilers. It is no longer part of the standard for C, but it is nevertheless, included in the very latest Pelles C versions.
    Quote Originally Posted by Salem View Post
    You mean it's included as a crutch to help ancient programmers limp along without them having to relearn too much.

    Outside of your DOS world, your header file is meaningless.

  10. #10
    Registered User
    Join Date
    Sep 2008
    Posts
    54
    Quote Originally Posted by Elysia View Post
    Tsch, you know as well as I that that code is no better than the original.
    There are several examples to get rid of the trailing newline, and sscanf is probably the worst of those alternatives, especially when buffer sizes go unspecified.
    And what would u recommend then Elysia!

  11. #11
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    One of these:
    Code:
    strtok(str, "\n");
    or
    Code:
    p = strchr(str, '\n');
    if (p) *p = '\0';
    or
    Code:
    len = strlen(str);
    if (str[len-1] == '\n')
        str[len-1] = '\0';
    You may also want to consider the case when there isn't a newline in that place, and what you should do then (it means that the buffer wasn't big enough).
    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  12. #12
    Registered User
    Join Date
    Sep 2008
    Posts
    54
    Quote Originally Posted by matsp View Post
    One of these:
    You may also want to consider the case when there isn't a newline in that place, and what you should do then (it means that the buffer wasn't big enough).
    --
    Mats
    Mats you see, last night it was working on gets but that was on windows, when i tried it on ubuntu it still does what it was doin in the beginning. Im not sure if its what u guys say about the newline character, the problem it does is it skips the first input with fgets. Take a look:

    Code:
    printf("\nEnter Customer's Name: " );
    
           scanf("%s", data[i].fname ); /* Read the horse's name */
    
           printf("Enter %s's Last Name: ", data[i].fname );
    
           scanf("%s", data[i].lname );
    
           printf("Enter %s's Age: ", data[i].fname );
    
           scanf("%d", &data[i].age );
    
           printf("Enter %s's Date Of Birth:Format(28/06/89): ", data[i].fname );
    
           scanf("%d", &data[i].day );
    
           printf("\r\r");
    
           scanf("%d",&data[i].month);
    
           printf("\r\r");
    
           scanf("%d",&data[i].year);
    
           printf("Enter %s's Street Address: ", data[i].fname );
    
           fflush(stdin);
    
           fgets(data[i].staddress,sizeof (data[i].staddress),stdin);
    
           printf("Enter Country Location of %s: ", data[i].fname );
    
           fflush(stdin);
    
           fgets(data[i].country,sizeof (data[i].country),stdin );
    Is it there garbage in the stdin?
    Last edited by AvaGodess; 11-04-2008 at 10:23 AM.

  13. #13
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Ah, sorry. I thought we were talking about getting rid of the newline that sits inside the buffer when you use fgets().

    I would suggest that you do not MIX fgets() and scanf() - it will fail sooner or later. Use fgets() to read the data, then use sscanf() if you need to get integer/float data out of the input string. If you need text input, use the above tricks to remove the newline at the end of your input [most likely, you do not want that].

    As stated fflush(stdin) doesn't work to remove newlines (or other stuff) from the input in all systems - it only works in Turbo C and Microsoft C as far as I'm aware. Certainly not in Linux.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  14. #14
    Registered User
    Join Date
    Sep 2008
    Posts
    54
    Quote Originally Posted by matsp View Post
    Ah, sorry. I thought we were talking about getting rid of the newline that sits inside the buffer when you use fgets().

    I would suggest that you do not MIX fgets() and scanf() - it will fail sooner or later. Use fgets() to read the data, then use sscanf() if you need to get integer/float data out of the input string. If you need text input, use the above tricks to remove the newline at the end of your input [most likely, you do not want that].

    As stated fflush(stdin) doesn't work to remove newlines (or other stuff) from the input in all systems - it only works in Turbo C and Microsoft C as far as I'm aware. Certainly not in Linux.

    --
    Mats
    Cool, thats something new for me today. I guess thats why it works on windows and not on ubuntu then. So what u are suggesting is to follow something like what Matt did on his post, before Elysia right. Ill try that.

  15. #15
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Yes, but don't use scanf() to read out string data. If you feel that you need to read into a large buffer and then crop it off, use strncpy. Otherwise, you can read into the actual buffer. In both cases, you need to make sure you remove the newline that is at the end of the input. [if there isn't one, the data you received is too long to fit in the buffer, and you probably should care about that case in a proper application - but I'll leave that to you to decice].

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Alice....
    By Lurker in forum A Brief History of Cprogramming.com
    Replies: 16
    Last Post: 06-20-2005, 02:51 PM
  2. Debugging question
    By o_0 in forum C Programming
    Replies: 9
    Last Post: 10-10-2004, 05:51 PM
  3. Question about pointers #2
    By maxhavoc in forum C++ Programming
    Replies: 28
    Last Post: 06-21-2004, 12:52 PM
  4. Question...
    By TechWins in forum A Brief History of Cprogramming.com
    Replies: 16
    Last Post: 07-28-2003, 09:47 PM
  5. Question, question!
    By oskilian in forum A Brief History of Cprogramming.com
    Replies: 5
    Last Post: 12-24-2001, 01:47 AM