为什么建议在scanf格式字符串中添加前导空格?

Sta*_*ley 6 c string controls scanf

我目前正在阅读这本书"初学者的C11编程",并在scanf()章节中说:

"始终在第一个控制字符串字符前添加前导空格,以确保准确的字符输入." 如:

scanf(" %s", whatever);
Run Code Online (Sandbox Code Playgroud)

控制字符串%s,前面有一个空格.我知道这听起来很不言自明,但我并没有真正得到可能出错的地方,以及这个空间如何确保准确的字符输入.

提前致谢.

chu*_*ica 5

@WhozCraig 很好地说明了这个建议的缺点。它没有理性也没有细节。此外,它不适用于有或没有前导空格的"%s"as"%s"消耗前导空格。

前导空格,无论是' ', '\t','\n'等都做同样的事情:直接scanf()使用而不是存储可选的前导空格char。这是因为以前的典型用法有用scanf()不消耗用户的'\n'距离Enter

scanf("%d", &some_int);
scanf("%c", &some_char);  // some_char is bound to get the value '\n'
Run Code Online (Sandbox Code Playgroud)

所有scanf()输入说明符都忽略前导空格,除了 3: "%c", "%n", "%[]"

简单指令确实受益于前导空间,如下所示。之前的剩余空白在 之前被消耗'$'

int Money;
scanf(" $%d", &Money);
Run Code Online (Sandbox Code Playgroud)

通常,尽管并非总是前导空格在"%c"阅读单个char用户输入时是有益的。

char ch;
scanf(" %c", &ch);
Run Code Online (Sandbox Code Playgroud)

该建议最错误的地方是 1) 在使用时"%s",提供宽度参数对于健壮的代码是必不可少的,并且 2) 应该检查返回值。

char buf[30];
int cnt = scanf("%29s", buf);
if (cnt != 1) Handle_NoInput_or_EOF_IOError();
Run Code Online (Sandbox Code Playgroud)

最后,建议使用fgets()scanf()作为一个能-这是通常的情况。

  • @Stanley `scanf(" %c", &ch);` 将消耗并丢弃可选的前导空格。然后将在 `ch` 中存储一个非空白的 `char`。`scanf("%c", &ch);` 将存储进入 `ch` 的第一个 `char`。`"%n"` 或 `"%[]"` 的工作方式完全不同。 (3认同)