我首先声明的char []不会被sscanf函数读入。
char rd[4];
char rs[4];
char rt[4];
sscanf(line, "or $%[^,], $%[^,], $%s", rd, rs, rt);
printf("RD: %s, RS: %s, RT: %s\n", rd, rs, rt);
例如,我把rd放在第一位,而rd没有被读入。我把rs放在第一位,它没有被读入。
这是我正在阅读的字符串: “或$ a0,$ t4,$ 0”
任何人都可以解释这个吗?
答案 0 :(得分:0)
几乎可以肯定,因为你的角色数组不够大,无法容纳你正在阅读的所有数据。具体来说,字符串"zero"
(带有\0
终结符)需要五个字节,而不是四个字节。超出数组末尾的写法是未定义的行为,一旦你这样做,所有的行为保证都会消失。
例如,当您声明:
时char rd[4];
char rs[4];
char rt[4];
你可能正在布局这样的记忆:
rt: [1] [2] [3] rs: [1] [2] [3] rd: [1] [2] [3]
+---+---+---+---+---+---+---+---+---+---+---+---+
| | | | | | | | | | | | |
+---+---+---+---+---+---+---+---+---+---+---+---+
并执行命令:
sscanf ("or $a0, $t4, $zero", "or $%[^,], $%[^,], $%s", rd, rs, rt);
可能导致内存块按所示顺序填充,导致以下内存写入,其中.
代表\0
:
rt: [1] [2] [3] rd: [1] [2] [3] rs: [1] [2] [3]
+---+---+---+---+---+---+---+---+---+---+---+---+
| | | | | a | 0 | . | | | | | |
+---+---+---+---+---+---+---+---+---+---+---+---+
+---+---+---+---+---+---+---+---+---+---+---+---+
| | | | | | | | | t | 4 | . | |
+---+---+---+---+---+---+---+---+---+---+---+---+
+---+---+---+---+---+---+---+---+---+---+---+---+
| z | e | r | o | . | | | | | | | |
+---+---+---+---+---+---+---+---+---+---+---+---+
导致最终情况:
rt: [1] [2] [3] rd: [1] [2] [3] rs: [1] [2] [3]
+---+---+---+---+---+---+---+---+---+---+---+---+
| z | e | r | o | . | 0 | . | | t | 4 | . | |
+---+---+---+---+---+---+---+---+---+---+---+---+
您可以看到rd
覆盖rt
是因为它看起来没有被rd
读入。
现在注意使用上面的单词may
,无法保证记忆将以这种方式布局,这只是对结果发生原因的一种可能解释。
最重要的是,您不应该将更多数据读入数组而不是您允许的数据。
至于如何解决这个问题,有很多可靠的方法可以在C中获取输入,例如this one。