克服跟随误差的方法是什么?



看下面的代码:

printf("Enter name and salary of 'Employee 1':n");
scanf("%49[^n]%*c,%d", name1,&salary1);

输入值为:

Harry Wilson
12000

下一个回显这些值的代码:

puts(name1);
printf("%d",salary1);

输出为:

Harry Wilson
118592

name1的输出正常,但salary1内部存在一个垃圾值。建议我防止这种错误的方法!!我想要与employee2相同的输入,但是当我尝试这样做时,它甚至无法接受输入。

scanf读取输入并尝试将其与传递给scanf的格式字符串匹配。只要输入与格式字符串匹配,它就会继续读取,如果不匹配,它就会停止读取。

让我们仔细看看你的格式字符串。

Format string: %49[^n]%*c,%d
%49[^n] means: Keep reading characters until a newline is found or 49 characters has been read
%*c means: Read the next character an discard it
, means: Read a comma
%d means: Read any number of white spaces (incl. zero) followed by an integer

你的输入是' "Harry Wilsonn12000n"这意味着:

input is: Harry Wilsonn12000n
Format %49[^n] will match the Harry Wilson and then
input is: "n12000n"
Format %*c will match the first n and then 
input is: "12000n"
Format , will not match and scanf will return leaving 12000n in the input stream

所以你的问题是逗号。要么从格式字符串中删除它,要么更改输入以在正确位置包含逗号。还要注意,%*c是不必要的,因为%d也会读取(并丢弃)整数值前的换行符。

如果"逗号"问题解决了,新的问题又会冒出来。在成功扫描整数值之后,输入流中会有一个n。这可能会干扰任何后续的scanf调用。考虑在格式字符串的第一个字符中添加一个空格,以删除输入流中的初始空白。

指出:

考虑使用fgetssscanf(或类似的解析器)代替scanf。它将在解析用户输入时为您提供更好的控制。举个例子:考虑一下如果用户输入一个100个字符长的名字,当前代码会发生什么。

对于sscanfscanf,总是检查返回值,因为它告诉我们匹配了多少个输入项。

您可以通过使用正确的语法输入来防止错误:

Harry Wilson
,12000

让你扫描成功并回显:

Harry Wilson
12000

这是因为代码要求第一个"任意字符""%c*"必须是换行符(因为之前的"%49[^n]"中的^n)并被忽略,即不写入任何接收变量。然后它需要一个特定的","

检查scanf()的返回值将帮助您获得正确的结果。
只要返回值不符合预期,扫描就会失败,任何进一步的扫描尝试都会遇到意外的输入,这可能会使它们失败。

或者,您可以更改代码以匹配输入。
可以修改scanf格式。
或者,正如已经在评论中推荐的那样,通过使用fgets()读取容易出错的输入(即人类键入的任何内容),并使用非破坏性的sscanf()尝试解析它。(scanf()消耗输入…)。

最新更新