简体   繁体   中英

How to use scanf to scan for multiple words?

I am trying to work on a function that take the input, the minimum character limit and the maximum character limit. I need to accept the input and count the letters even if there are 2 words or more, and I saw people said scanf("%30[^\n]%*c") would do the trick. However, this only work if it is the first input ever, nothing more. If there has been any input above, it would just terminate the line, leaving count as zero, and run the loop infinitely. Anyone knows why?

NOTE: I can not use anything from the <string.h> header file.

{
    int n = 1;
    
    while (n == 1)
    {
        int count = 0;
        scanf("%30[^\n]%*c", input);
        while (input[count] != '\0')
        {
            count++;
        }
        if (minimum == maximum)
        {
            if (count > maximum)
            {
                printf("String length must be exactly %d chars: ", minimum);
            }
            else if (count == minimum)
            {
                n = 0;
                return input;
            }
            else if (count < minimum)
            {
                printf("String length must be exactly %d chars: ", minimum);
            }
        }
        else 
        {
            if (count > maximum)
            {
                printf("String length must be no more than %d chars: ", maximum);
            }
            else if (minimum <= count && count <= maximum)
            {
                n = 0;
                return input;
            }
            else if (count < minimum)
            {
                printf("String length must be between %d and %d chars: ", minimum, maximum);
            }
        }
    }
}

The problem with scanf("%30[^\n]%*c", input); is it fails if the new byte from stdin is a newline, returning 0 and leaving input unchanged, potentially uninitialized, causing the rest of the code to have undefined behavior.

Also note that this format will cause scanf() to read and discard the byte pending after the conversion, either the newline, which is your intent or whatever 31st character was typed by the user on the input line.

You should test the return value of scanf() to detect a conversion error and/or the end of file and only scan the array if scanf() returns 1 .

You should discard extra bytes at the end of the line with a loop:

int c;
while ((c = getchar()) != EOF && c != '\n')
    continue;

Or with scanf() :

scanf("%*[^\n]");  // discard the rest of the input line if any
scanf("%*c");      // discard the newline if any.

To get rid of the pending newline left from previous calls to scanf() , you can write:

int c;
if ((c = getchar()) != '\n')
    ungetc(c, stdin);

Or using scanf :

scanf("%1*[\n]");  // read and discard at most 1 newline byte

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM