第一个格式字符串字符不是空格时 scanf 的行为

问题描述 投票:0回答:2

scanf 应该消耗并丢弃格式字符串中不属于转换说明符的任何字符。但当非空白、非转换字符出现在格式字符串的前面时,其行为似乎有所不同。为什么?

int main() {
    int num, num2;
    printf("> ");
    while (scanf("> %d %d", &num, &num2)) {
        printf("You entered the number %d %d.\n", num, num2);
        printf("> ");
    }
    return EXIT_SUCCESS;
}

如果您构建并运行它并在提示符下输入 > 3 4,它将打印消息和重复的提示,然后立即退出。因此,这意味着 scanf 第一次返回 2,然后在用户输入另一组标记之前返回 0。如果从格式字符串中删除“>”,循环将一直运行,直到用户输入非数字的内容,导致 scanf 返回 0——这是我期望的行为。另外,如果我在第一个转换说明符之后放置相同的符号,则循环将继续按预期运行。也就是说,如果格式字符串具有 "%d > %d",并且用户输入 3 > 4,则循环将再次运行并接受另一轮输入。我还没有看到任何有关此行为的文档。谢谢!

c scanf format-string
2个回答
0
投票

来自 fscanf 上的一些

文档

格式字符串包含

  • %
    之外的非空白多字节字符:格式字符串中的每个此类字符 从输入流中消耗完全相同的一个相同字符,或者如果流中的下一个字符不相等,则导致函数失败。

虽然

fscanf
说明符
%d
消耗所有前导空格,但它消耗后面的换行符,并且
'>'
完全匹配换行符(
'\n'
)在后续迭代中。


旁白:这将在EOF

truthy
返回值上永远循环(负数
int
,几乎普遍都是
-1
):

while (scanf("> %d %d", &num, &num2))

用途:

while (2 == scanf("> %d %d", &num, &num2))

或者干脆避免

scanf
进行此类任务。


0
投票

我基本上同意所有评论,尤其是那些强调

scanf
对于用户输入来说并不是一个好主意的评论。您的问题的答案也大部分得到了回答,在第一次输入后,换行符“字符”保留在缓冲区中,第二个循环将匹配该换行符将与说明符中的第一个字符匹配,并且它将失败,停止循环。

按照建议,在说明符的开头添加一个空格将强制 scanf 消耗所述换行符并清除输入缓冲区,该缓冲区将再次等待输入。

© www.soinside.com 2019 - 2024. All rights reserved.