💻前言
🍁介绍分析getchar函数以及其在缓冲区的应用
💻.1 getchar函数与缓冲区
首先我们知道是getchar是用来获取一个字符的,而对应的putchar函数可以用来打印一个字符
getchar函数的返回值是用户输入字符所对应的ASCII码,若遇到文件结尾(End-Of-File)或者读取时遇到错误则返回EOF(-1),且将用户输入的字符回显到屏幕。
当使用getchar获取一个字符的时候,其实它不是从我们的键盘上直接获取的,在计算机的内存内存空间中存在一个 缓冲区。
1.缓冲区又称为缓存,它是内存空间的一部分。也就是说,在内存空间中预留了一定的存储空间,这些存储空间用来缓冲输入或输出的数据,这部分预留的空间就叫做缓冲区。
2.缓冲区根据其对应的是输入设备还是输出设备,分为输入缓冲区和输出缓冲区。
看下面这段代码
#include<stdio.h> int main() { int ch = 0; while ((ch = getchar())!=EOF) { //printf("%c",ch); putchar(ch);//与printf打印一样的效果 } return 0; }
看程序的执行过程,实质上当我们从键盘上输入一个字符时,这个字符是先存放在缓冲区当中等待getchar进行读取;
当我们在键盘上敲入回车后,getchar便会读取缓存区中的一个字符,而敲回车换行进行输出,实际上敲回车又在缓冲区放入了一个\n,在下一次循环getchar会将这个\n读走,所以输出一个字符后便自动换行了;
当输入^Z(Ctrl+z)时,getchar读取后会返回一个EOF,循环结束(VS编译器中可能需要按三次Ctrl+z,算是VS编译器的一点小问题,其他的编译环境正常一次即可)。
getchar使用实例:只打印数字字符,跳过其他字符的,代码如下。
#include<stdio.h> int main() { int ch = 0; while ((ch = getchar())!=EOF) { if (ch<'0'||ch>'9') { continue; } putchar(ch); printf("\n"); } return 0; }
💻.2 getchar清理缓存区
看这样一个代码,输入一个密码,然后进行确认密码。
#include<stdio.h> int main() { int password[20] = { 0 }; printf("请输入密码:>"); scanf("%s", password);//假设密码是abcdef printf("请确认密码(Y/N):>"); int ret = getchar(); if (ret == 'Y') { printf("确认成功\n"); } else { printf("确认失败\n"); } return 0; }
看这里的运行结果,还没有输入Y/N进行确认,便已经输出了结果了
这里是因为我们在输入abcdef后,它只是在缓冲区等待进行读取,当我们在键盘上敲入回车后,在缓冲区放入了一个\n,scanf才会进行读取,要注意的是scanf在遇到空白符(如换行、空格等)会结束读取,所以scanf并不会去读取\n,getchar会将缓冲区中的\n读走进行判断结束了程序。
这里在scanf读走字符串后我们需要解决掉这个\n 才可以正常进行确认密码,也就是需要清理缓冲区 。
如果只是要清理上面的问题,我们只需要把缓冲区的\n清理掉即可,做法如下:
#include<stdio.h> int main() { int password[20] = { 0 }; printf("请输入密码:>"); scanf("%s", password); getchar();//清理\n printf("请确认密码(Y/N):>"); int ret = getchar(); if (ret == 'Y') { printf("确认成功\n"); } else { printf("确认失败\n"); } return 0; }
这里在scanf后加了一个getchar,当scanf读取结束后,getchar接着就会把缓冲区的\n清理掉;但这个方法只是可以临时解决问题,存在很大的弊端,看下面这个运行结果
当输入的密码中包含空格,因为scanf遇到空白符会结束读取;而这时scanf后的getchar只能清理一个字符,后面的qwer\n就无法被清理而导致无法正常进行密码的确认,所以说这种方法有时候无法完全清理缓冲区,原因是这里的getcher只能实现一次清理,而如果我们可以实现多次清理就可以解决这个弊端。
下面是优化后的清理缓存区的代码。
将scanf后的getchar换成
while ((ch = getchar()) != ‘\n’)
{
;
}
这条循环语句会让getchar逐个清理缓存区的字符,直到将最后的\n清理掉循环结束.
#include<stdio.h> int main() { int password[20] = { 0 }; printf("请输入密码:>"); scanf("%s", password); //getchar(); int ch = 0; while ((ch = getchar()) != '\n') { ; } printf("请确认密码(Y/N):>"); int ret = getchar(); if (ret == 'Y') { printf("确认成功\n"); } else { printf("确认失败\n"); } return 0; }
💻结语
各位小伙伴,看到这里就是缘分嘛,希望我的这些内容可以给你带来那么一丝丝帮助,可以的话三连支持一下呗(关注✌️点赞✌️评论✌️)!!!
感谢每一位走到这里的小伙伴,我们可以一起学习交流,一起进步!!!加油!!!