为什么 printf() 不给出任何错误和 scanf() 问题

Why printf() don't gives any error and issue with scanf()

代码:

int main(int argc,char **argv)
{
  int y,i;
  printf("Number of character you entered is : %d",printf("you entered age : %d\n",i,scanf("%d",&i),printf("Enter age : "))-19);
  printf("\n\n");
  scanf("%d ",&y,printf("Enter number(y) : "));
  printf("Value of y is %d",y);
}

这里有两个声明, 在第一个声明中,我想问为什么 printf() 不给出任何错误或警告?

printf("Number of character you entered is : %d",printf("you entered age : %d\n",i,scanf("%d",&i),printf("Enter age : "))-19);

执行时的第二条语句要求输入两次,第一次是在

之后

"Enter number(y) : "

输入数字后要求再次输入,不知道为什么。

y的值是你第一次输入的值那么第二次输入是怎么回事?

scanf("%d ",&y,printf("Enter number(y) : "));

它不要求输入 "two times" 而是 scanf() 正在等待您输入非 space 白色 space 字符以终止输入读取,因为格式字符串中的额外 space:"%d ".

scanf() 中的 whitespace 指令将读取并丢弃任意数量的 whitespace 字符。因此,你被迫输入一个非白色space字符:

scanf manual 状态:

· A sequence of white-space characters (space, tab, newline, etc.; see isspace(3)). This directive matches any amount of white space, including none, in the input.

在任何情况下,您传递给 scanf() 的参数比您传递的格式说明符太多,这是一种通过单个语句传递打印和扫描输入的糟糕方式。

对于第一个 printf() 语句,引用 C11 标准,第 7.21.6.1 章,fprintf()

If the format is exhausted while arguments remain, the excess arguments are evaluated (as always) but are otherwise ignored.

所以,没有产生错误。

scanf() 的情况下,问题出在

 scanf("%d ",&y,printf("Enter number(y) : "));
          ^
          |

格式说明符后的尾部白色-space。基本上它告诉在第一个匹配转换说明符的输入之后忽略 任意数量的尾随白色-space。遇到非白色-space字符时,它实际上会完成扫描

引用章节 §7.21.6.2

A directive composed of white-space character(s) is executed by reading input up to the first non-white-space character (which remains unread),.....

解决方法:去掉转换说明符后面的尾部白色-space。

scanf("%d",&y,printf("Enter number(y) : "));

FWIW,即使参数超过格式字符串中的转换说明符的参数也被定义为行为,如 C11,第 7.21.6.2 章

If the format is exhausted while arguments remain, the excess arguments are evaluated (as always) but are otherwise ignored.

这是一种可怕的代码编写方式。