【发布时间】:2014-05-12 14:33:10
【问题描述】:
出于某种原因,我无法让fgets() 和strcat() 的两个实例工作。
这是我的代码:
#include <stdio.h>
#include <string.h>
int main()
{
char str[150];
char userName[8]; char password[8];
printf("Enter username: ");fgets(userName, 9, stdin);
printf("Enter password: ");scanf("%s", password);
strcpy(str, "INSERT INTO USERS (ID,USERNAME,PASSWORD,IP) " \
"VALUES (1, '");
strcat(str, userName);
strcat(str, "', '");
strcat(str, password);
strcat(str, "', '120.132.12.1');");
puts(str);
return 0;
}
当获取“密码”的字符串时,我不能使用fgets() 或者它会抛出错误“中止陷阱:6”。具体来说,我正在使用:
fgets(password, 9, stdin);
9 个元素,因为我读到您需要在总数中考虑空终止字符。
我不明白这一点,因为 char 数组中的元素与 userName 一样多,我认为获取字符串的代码应该与 char 数组名称几乎相同。
此外,strcat() 在尝试将“str”附加到用户名时似乎不起作用。我的输出看起来像这样:
Enter username: beckah12
Enter password: beckah12
INSERT INTO USERS (ID,USERNAME,PASSWORD,IP) VALUES (1, '', 'beckah12', '120.132.12.1')
为什么会跳过"strcpy(str, userName)"?
更新
当我声明这两个字符串时存在一些内存重叠。当我在两个字符串之间声明一个随机整数时,它保留了两者的输入。如何通过更持久的解决方案修复此内存重叠?
【问题讨论】:
-
fgets()的第二个参数太大。对于char[8],它应该是8。此外,您应该限制(并验证)scanf:scanf("%7s", password); -
可能发生的情况是密码的空终止符存储在用户名的第一个字节中,从而使用户名看起来好像是一个空字符串(实际上,它 is 如果此诊断正确,则为空字符串)。打印出读取密码前后
username的值。或者尝试 7 个字符的密码。 -
“不会等待”问题意味着
fgets()在读取换行符之前已经没有空间容纳该行数据;因此,第二个fgets()读取换行符并停止处理。将数据读入更大的字符串(32、64、80、256、4096 字节),然后验证长度等。请记住,fgets()在合适的情况下在输入字符串中包含换行符。当它不适合时,它会被留下来进行下一次读取操作。将用户名限制为 8 个字符,这有点古怪——有点 80 年代复古风,不是吗? -
输入“beckah12”时,您需要一个 10 或更多的缓冲区,因为
fgets()将读取"beckah12\n",即 9char和终止'\0'。 -
您编辑了您的问题以纠正(部分)您所询问的问题。请不要那样做;它会使已发布的答案无效,并使您的问题对未来的读者毫无用处。我已经回滚了编辑。