Program doesn't execute gets() after scanf(), even using fflush(stdin)

て烟熏妆下的殇ゞ 提交于 2019-11-27 09:38:12
emsworth

If flushing std doesn't work, then try reading in the extra characters and discarding, as suggested here.

This will work:

#include <string.h>
#include <stdio.h>

int main(){
    char nombre[10];
    char mensaje[80];
    int c;

    printf("Type your name:\n");
    scanf("%9s", nombre);

    while((c= getchar()) != '\n' && c != EOF)
            /* discard */ ;

    printf("Now, type a message:\n");
    gets(mensaje);

    printf("%s:%s",nombre,mensaje);
    return 0;
}

Two big, major issues:

  1. DO NOT USE fflush ON INPUT STREAMS; the behavior of fflush on input streams is not defined. Just because it appears to work in this situation does not mean it is correct.

  2. NEVER NEVER NEVER NEVER NEVER NEVER NEVER use gets - it was deprecated in the C99 standard and has been removed completely from the C2011 standard. It will (not might, will) introduce a major point of failure in your code.

It's never a good idea to follow a scanf call with a gets call, since gets won't skip over any leading newlines left in the input stream by scanf. Use scanf to read both nombre and mesaje.

printf("Type your name:\n");
scanf("%9s", nombre);

printf("Now, type a message:\n");
scanf("%79s", mensaje);

It's a good idea to use an explicit length specifier in the scanf call for %s and %[, otherwise you introduce the same security hole that gets does.

EDIT

D'oh. I'm an idiot. If you're trying to read a string containing spaces, you can't use the %s conversion specifier. Use the %[ conversion specifier instead:

scanf( "%79[^\n]", mensage );

That will read up to the next 79 characters or the newline, whichever comes first, and leaves the newline in the input stream.

Try this instead:

scanf("%s\n", nombre);

scanf stops at whitespace when reading a part. gets reads until the first new line. So what happens is scanf leaves behind a newline in the buffer, which gets immediately sees and thinks it was given a blank line.

If you take your original code and enter "name message", two pieces all on one line, you can see this in action - gets will still immediately return, but it will see the second part.

The \n in the scanf thing tells it to go ahead and consume that too.

Try gets(stdin); instead of

fflush(stdin);
user9816128
while (fgetc(stdin) != '\n'); // seems to work
标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!