[Solved] Why does my C program print messages twice if the user input is longer than 16 chars? [closed]


It works fine if I type in a < 5 characters userID, but when I type in a userID with more than 16 characters, the messages asking the user for a different userID are printed twice. Why’s that?

  • When you enter more than 16 characters, then 17 characters are scanned into the string userID as you have not entered '\n', no null character will be placed at the end of the string userID.

  • and then,when you use strlen(userID), this invokes Undefined behavior as there is no terminating \0 character placed at the end. try doing this :

  • and when you restart the iteration the remaining extra integers are taken in.


Solution :

To avoid the above problems:

  1. Place a null character at the position index + 1 over each iteration.
  2. flush the stdin at the end of each iteration.

    do
    {
        printf("Please choose your user ID! (it must be between 6 - 16 charaters long)\n");
    
        for (int i = 0; i < 17; i++)
        {
            userID[i] = getchar();
            userID[i+1] = '\0'; //placing null character at the position index+1
    
            if(userID[i] == '\n')
            {
                userID[i] = '\0';
                break;
            }    
    
        }
    
        fflush(stdin); //flushing the extra input at the end of each iteration
    
    } while (strlen(userID) < 7  ||  (strlen(userID) > 16  &&  userID[16] != '\n'));
    

sample input :

more than 16 123456789
1123
123456789

sample output :

Please choose your user ID! (it must be between 6 - 16 charaters long)
more than 16 123456789
Please choose your user ID! (it must be between 6 - 16 charaters long)
1123
Please choose your user ID! (it must be between 6 - 16 charaters long)
123456789

Your acount info are:
    userID  : 123456789
    passcode: 

NOTE :

Avoid using fflussh(stdin) as it has portability issues as suggested by @JonathanLeffler in the comments. Also here’s an explanatory post why not to use fflush(stdin) : click

Here’s an implementation of your code avoiding the use of fflush(stdin)

do
{
    int i;

    printf("Please choose your user ID! (it must be between 6 - 16 charaters long)\n");

    for (i = 0; (userID[i] = getchar()); i++)
    {

        userID[i+1] = '\0'; //placing null character at the position index+1

        if(userID[i] == '\n')
        {
            userID[i] = '\0';
            break;
        }

        //if user enters more than 16 characters then,
        //scan in 17th character for `strlen(userID)` purpose and
        //consume all other characters using an integer `c`
        if( i > 17)
        {
            int c;

            while( ((c = getchar())!= '\n') && (c!=EOF) );
            break;
        }
    }

} while ( (strlen(userID) < 7)  ||  (strlen(userID) > 16 ) );

4

solved Why does my C program print messages twice if the user input is longer than 16 chars? [closed]