【C】学习笔记:scanf与键盘输入缓冲区

最近老陌偶然从论坛的一个帖子里发现了以前忽略了的一个知识点,看了一些资料后不得不感慨自己之前对于 scanf 对于 C 的理解实在太浅显了!最后我打算把本次学习所得写出来……

double get_input(void)
{
    double a;
    char ch;
    while(scanf("%lf",&a)!=1)
    {
        while ((ch=getchar())!='\n')
            putchar(ch);
        printf("\nEnter a number\n");
    }
    return a;
}

while(scanf("%lf",&a)!=1)  // 输入的是double内容,那么while循环体不执行; 如果不是double,键盘缓冲区的内容并没有变化,还是原来的内容,所以一直在这儿死循环   

  while(scanf("%lf",&a)!=1)    {   // 输入的不是一个double类型数据, 会进入这个while循环体 
        while ((ch=getchar())!='\n') // 把缓冲区的字符一个一个的提取出来, 包括最后的回车符, 也就是放弃了这一整行的数据了

后面的这个函数,因为可以把键盘缓冲区清空,让用户重新输入数据,所以可以继续进行下去
前面的那个函数,因为没有清理缓冲区, 所以读取double的条件始终无法达到

C标准规定 fflush()函数是用来刷新输出(stdout)缓存的。对于输入(stdin),它是没有定义的。但是有些编译器也定义了 fflush( stdin )的实现,比如微软的VC。其它编译器是否也定义了 fflush( stdin )的实现应当查找它的手册。GCC编译器没有定义它的实现,所以不能使用 fflush( stdin )来刷新输入缓存。

对于没有定义 fflush( stdin )的编译器,可以使用 fgets()函数来代替它(比用 getchar()、scanf()等函数通用性好)。可以这样忽略输入流中留下的回车等其它输入,从而使下一次的输入总保持一个“干净”的状态。(这个是任何平台下都可以的)

功能:清空输入缓冲区,通常是为了确保不影响后面的数据读取(例如在读完一个字符串后紧接着又要读取一个字符,此时应该先执行fflush(stdin);)。

fflush(stdin)仅适用于部分编译器(如VC6),但是并非所有编译器都要支持这个功能(如gcc3.2)。这是一个对C标准的扩充。在linux下用的是gcc,因此可能不起作用。

键盘的内部有一块微处理器,它控制着键盘的全部工作,比如主机加电时键盘的自检、扫描,扫描码的缓冲以及与主机的通讯等等。当一个键被按下时,微处理器便根据其位置,将字符信号转换成二进制码,传给主机和显示器。如果操作人员的输入速度很快或CPU正在进行其它的工作,就先将键入的内容送往内存中的键盘缓冲区,等CPU空闲时再从缓冲区中取出暂存的指令分析并执行

scanf支持正则

scanf(“%*[^\n]%*c”);

 

参考资料:

键盘缓冲区

scanf 清缓冲区的问题 

fflush(stdin)

scanf()中清除输入缓冲区的几种方法归纳

『踩坑记录』scanf输入缓冲区的问题

c语言输入输出缓冲区的概念

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值