我想知道为什么 int 的两个值不验证 if 条件,即使它是 true。 printf 显示两者相等。
缓冲区溢出是否会影响 if 条件的行为,从而破坏其他代码段的行为。
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
int main(void) {
srand(time(NULL));
char instring[2]; // when this increases somehow I get the right behavior
int inint;
int guess;
guess = rand() % 127;
inint = ~guess;
printf("%i\n", guess); //testing with printf()
while (guess != inint) {
printf("Guess Number\r\n");
gets(instring);
inint = atoi(instring);
printf("%i\n", inint);
if (inint > guess) {
printf("%i\n", inint);
puts("too high");
} else if (guess > inint) {
puts("too low");
} else {
puts("right");
}
}
return 0;
}
最佳答案
问题确实出在这里。
char instring[2];
现在让我们考虑一下这一行。
gets(instring);
假设您输入 10
并按 Enter 键。 instring
中将包含三个字节。
1
0
- 终止 null。
instring
只能容纳两个 个字节,但gets
无论如何都会塞入(至少)三个 字节。该额外的字节将溢出到相邻的内存中,从而破坏其他一些变量的内存,从而导致一些奇怪的错误。
这就是为什么使 instring
足够大以容纳 gets
的结果来修复程序。
为了在处理字符串时避免这种情况,请使用将自身限制为可用内存的函数。在这种情况下fgets
.
fgets(instring, sizeof(instring), stdin);
这将限制自己只能读取 instring
所能容纳的内容。
一般来说,不要吝惜内存来读取输入。一种常见的做法是分配一个大缓冲区来读取输入,1024 是好的,并重用该缓冲区仅用于读取输入。数据被复制到大小更合适的内存中,atoi
可以有效地为您完成这项工作。
关于C 字符串行为和 atoi 函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49850276/