浅析printf和scanf的用法与返回值

printf: 向屏幕输出数据
%d: 输出十进制的整型数据
%f:  输出浮点数,float和double都可以
%c: 输出字符
%s: 输出字符串
%x: 输出十六进制的数据,如果有字母,字母小写输出   1000->3e8
%X: 输出十六进制的数据,如果有字母,字母大写输出   1000->3E8

scanf: 从键盘读取数据
但是我们不建议使用scanf读取数据,为什么呢?
1.容易出错
#include
int main()
{
 float c,d;
 scanf("%f %f",&c,&d);
 printf("%f,%f\n",c,d);
 return 0;
}
我们写这样一个程序,读取两个数据,然后输出,第一次我们这样输入输出没有任何问题
浅析printf和scanf的用法与返回值
第二次在scanf中加入了一个逗号,第二个数的输出便出现了问题

浅析printf和scanf的用法与返回值
我们加上一个逗号,又是正常的输出了,因为我们输入的时候,scanf里面的内容都要输入,我们没有输入逗号,编译器就读取不到我们后面输入的数字

浅析printf和scanf的用法与返回值
我们可能想在scanf 里面也加上一个\n表示换行,但是我们无论怎么换行,都输出不了

浅析printf和scanf的用法与返回值
但是当我们加上一个\n一起输出的时候,又可以正常的读取数据了,是因为scanf中\n并不表示换行,而是和普通的字符一样。

浅析printf和scanf的用法与返回值
所以由以上测试可以看出,scanf并不太好用,我们可能经常会忽略一些细节的东西,使运行失败。
如果想要输入一个数据的话,直接在函数的参数列表传参就好了。
2.当写测试用例的时候,非常的不方便
把a,b,c三个数从大到小输出
#include
void Sort(int a,int b,int c)
{
 int tmp;//临时变量
 if(a>b)
 {
  tmp=a;
  a=b;
  b=tmp;
 }
 if(a>c)
 {
  tmp=a;
  a=c;
  c=tmp;
 }
 if(b>c)
 {
  tmp=b;
  b=c;
  c=tmp;
 }
 printf("%d,%d,%d\n",a,b,c);
}
int main()
{
 Sort(10,20,30);
 Sort(20,10,30);
 Sort(30,20,10);
 Sort(20,30,10);
 Sort(20,-1,0);
//以上几行都是测试用例
 return 0;
}
当我们要检测一个程序有没有bug时,要写很多的测试用例,如果我们用scanf进行测试,因为一直在运行窗口输入数据,当输入结束后,刚刚输入的数据我们已经忘掉了,后面测试的时候可能会进行重复测试,非常的不方便。另一方面,如果这个程序真的有bug需要我们改正的时候,我们还要对改变后的程序进行测试用例,又要再来一遍,可能还会出现上面的情况。但是如果我们调用函数,这两个情况就都不会有,因为函数不能重复调用,而且即使出错了,我们只需要把错误的位置改过来,不需要担心测试用例,它就在程序里面。所以可以看出用scanf是非常不方便的。


printf返回值:
printf函数原型为 int  printf(char *format,args,...)
format:按原型输出
args:打印几个字符,就返回几

例如:
int a=36;
printf("%d",printf("%d",a));
输出:
362

printf("%d\n",printf("%d\n",i));
输出:
36
3
输出36,原样输出,36是两个字符,所以第一个返回值是2.
第二个加上了换行,所以返回值又多了一个换行的字符,所以第二个换行了,并且变成了3
int b=5396401;
printf("%d",printf("%d",printf("%d",b)));
 输出:
539640171
 printf("%d\n",printf("%d\n",printf("%d\n",b)));
输出:
5396401
8
2
根据以上两个例子可以看出,printf原样输出值,而它的返回值就是输出的值有几个字符,就返回几。

scanf的返回值:
scanf函数的原型是 int scanf(char *format[,argument,....]);
int a,b;
 int t=scanf("%d,%d",&a,&b);
 printf("%d\n",t);
运行:
输入:2,3
输出:2
运行:
输入:435,234
输出:2
为什么输入了不同的值输出都是2 呢,应该与输入值的字符长度没有关系,是不是和变量有关系呢,我们在加一个变量试一试。
int a,b,c;
 int t=scanf("%d,%d,%d",&a,&b,&c);
 printf("%d\n",t);
运行:
输入:2,3,4
输出:3
运行:
输入:234,6,14
输出:3
这时,我们可以确定scanf的返回值和变量有关了。那么返回值是变量的个数吗?
再想一个问题,如果我们给变量赋值的时候,发生了错误,会出现什么情况呢?
char  a,b,c;
 int t=scanf("%c,%c,%c",&a,&b,&c);
 printf("%d\n",t);
 运行:
输入:a,b,c
输出:3
没有错误和我们想的一样
运行:
输入:a,b,1900
输出:3
虽然输入值的类型与变量值的类型不匹配,但是输出的结果依然是3
 char  a,b,c;
 int t=scanf("%c,%c",&a,&b,&c);  
 printf("%d\n",t);
运行:
输入:a,b,c
输出:2
因为scanf只能读到两个数,所以输出就是2
可以看出scanf的返回值是接收到的变量个数。