在初学C/C++语言时,有人会遇到这样的问题,就是连续的printf和scanf可能导致某些输入不能正常输出,或者导致某些scanf语句甚至getchar被跳过。为什么会出现这种情况呢?坐标来分享。
工具/原料
电脑
C-free
方法/步骤
1、我们咸犴孜稍先来看一种情况。#include<stdlib.h>#include<stdio.h>intmain(){ ch锾攒揉敫ar*name,*no; charflag; do{ printf("请输入姓名:"); scanf("%s",&name); printf("请输入学号:"); scanf("%s",&no); printf("\n\n按任意键继续输入,退出请输入q!\n\n"); scanf("%c",&flag); }while(flag!='q'); return0;}在逻辑上,这种是不会出错的,那么实际运行情况如何呢?输入学号回车后,直接跳到下一次输入,也就是跳过了scanf("%c",&flag);的执行。
2、我们调试来看。我们将断点设置在printf("\n\n按任意键继续输入,退出请输入q!\n\n");语句这里。
3、单步执行后,没有输入,flag的值被赋值为10,相应的ascii值是回车符。
4、那么我们把scanf("%c",&flag);改写成scanf("%s",&flag);来执行看看。结果是接收输入,也运行正常了。
5、但是,作为一个char类型的变量,用字符串的输入方式虽然程序能正常运行,但是这种做法是不安全的。通过下图我们可以看到每次都只取第一个字母。
6、那么,为什么会出现这种情况?这种情况应该耦嘀扔硇怎么解决呢?这种情况的出现是因为用户在输入结束时都会敲一下回车键才能让程序继续执行,但块吧吨翘是,每次printf会从用户输入缓冲区取出用户输入的内容,这样就会在缓冲区留下回车键,下一次输入如果是获取一个字符,就会将缓冲区剩余的回车键取出。
7、有朋友会问:那为什么用scanf("%s",&flag);就可以正常运行呢?这是因为编译器对字符串的处理是:从第一个字符不为空格、换行、回车才开始的,因此会自动删除回车符,这样就保证了取到第一个有效的字符。
8、解决方案。了解了原理后,解决方案就出来了,我们可以在scanf输入char类型之前,用getchar()函数消除回车符的影响。但是需要注意的是,对于char类型的输入,我们一般不用scanf,尽量用gechar()。
9、修改后的代码。#include咯悝滩镞<stdlib.h>#include<stdio.h>intmain(){ char*name,*n泠贾高框o; charflag; do{ printf("请输入姓名:"); scanf("%s",&name); printf("请输入学号:"); scanf("%s",&no); printf("\n\n按任意键继续输入,退出请输入q!\n\n"); getchar();//消除回车符的影响。 flag=getchar();//接收判断字符。 }while(flag!='q'); return0;}