我正在尝试制作一个小型帐户注册程序。它提示用户输入 userID
和password
。我正在研究 userID
部分,但似乎不对。如果我输入 < 8
,效果很好。字符userID
,但是当我输入 userID
超过16
字符,询问用户不同的消息 userID
打印两次。这是为什么?
#include <stdio.h>
#include <string.h>
#include <ctype.h>
int main(void)
{
// Setting up variables
char userID[18];
char passcode[51];
// Firstly promt the user for user ID
do // This loop is for asking the user to type another userID if his chosen one isn't approprite
{
printf("Please choose your user ID! (it must be between 6 - 16 charaters long)\n");
for (int i = 0; i < 17; i++) // This loop store the userID into the character array
{
userID[i] = getchar(); // Store userID into array character by character
if (userID[i] == '\n')
{
userID[i+1] = '\0';
break;
}
}
}
while (strlen(userID) < 7 || (strlen(userID) > 16 && userID[16] != '\n'));
// Printing info on the screen.
printf("Your acount info are:\n\tuserID : %s\tpasscode: ", userID);
最佳答案
It works fine if I type in a
< 5
charactersuserID
, but when I type in auserID
with more than16
characters, the messages asking the user for a differentuserID
are printed twice. Why's that?
当您输入超过
<16
字符时,17
字符会被扫描到字符串userID
中,因为您没有输入'\n'
,不会在字符串userID
末尾放置空字符。然后,当您使用
strlen(userID)
时,这会调用未定义的行为,因为末尾没有放置终止\0
字符。尝试这样做:当您重新开始迭代时,剩余的额外整数将被吸收。
解决方案:
为了避免上述问题:
- 在每次迭代中在
index + 1
位置放置一个空字符。 flush
每次迭代结束时的stdin
。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'));
示例输入:
more than 16 123456789
1123
123456789
示例输出:
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:
<小时/>
注意:
避免使用 fflussh(stdin)
,因为它存在可移植性问题,如 @JonathanLeffler 中的 comments 建议。另外,这里还有一篇解释性文章为什么不使用 fflush(stdin)
:click
这是避免使用 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 ) );
关于c - 如果用户输入的长度超过 16 个字符,为什么我的 C 程序会打印两次消息?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38278125/