匠川 2016-09-19 14:05 采纳率: 100%
浏览 2180
已采纳

关于C语言中的getchar(),小白请教一个问题。

小白重新学C语言。
准备把K&R的The C programming language从头到尾学一遍。

然后今天敲到getchar()时,为了做练习1-6:验证getchar()!=EOF 是0还是1,我就写了下面的代码:

 main()
{
    int thischar,test=0;
    char flag = 0;

    while ((thischar=getchar()) != EOF)
    {   
        test = ((thischar = getchar()) != EOF);  //Q1.
        printf("The value of condition after putchar(): %d \n", test);
        flag = 1;
        //if ((thischar = getchar()) != EOF);   //test step
        while ((thischar = getchar()) != EOF && flag == 1)
        {
            putchar(thischar);
            //printf("\n");
        }
        flag = 0;

    }

输入“12345678”,输入就是“345678”。
缺少“12”。
我打开调试之后,发现thischar的值是这样变化的:

breakpoint1
breakpoint2

我查了ASCII码,对应的49,50就是1和2.
也就是说因为我多检测了两次

 (thischar = getchar()) != EOF

这个。就导致我输出少了两个字符。我之后又试了试,以此类推,条件数量增多少,输出的字符就会少多少。
网上说getchar()函数的代码是这样的:

    int  
    getchar ()  
    {  
      int result;  
      _IO_acquire_lock (_IO_stdin);  
      result = _IO_getc_unlocked (_IO_stdin);  
      _IO_release_lock (_IO_stdin);  
      return result;  
    }  

我也查了寄存器的说明,但是还是不明白,为什么会造成这样的情况。和getchar()这个函数的定义有关系吗?如果没有,那是哪里出的问题呢?

感激不尽!

追加:
谁能大概解释一下getchar()函数定义,用自然语言描述大概是什么样的过程?
以及:

 while ((thischar=getchar()) != EOF)
01064C89  mov         esi,esp  
01064C8B  call        dword ptr [__imp__getchar (0106916Ch)]  
01064C91  cmp         esi,esp  
01064C93  call        __RTC_CheckEsp (01061113h)  
01064C98  mov         dword ptr [thischar],eax  
01064C9B  cmp         dword ptr [thischar],0FFFFFFFFh  
01064C9F  je          main+0D3h (01064D33h)  
    {   
        test = ((thischar = getchar()) != EOF);  //Q1.
01064CA5  mov         esi,esp  
01064CA7  call        dword ptr [__imp__getchar (0106916Ch)]  
01064CAD  cmp         esi,esp  
01064CAF  call        __RTC_CheckEsp (01061113h)  
01064CB4  mov         dword ptr [thischar],eax  
01064CB7  cmp         dword ptr [thischar],0FFFFFFFFh  
01064CBB  je          main+69h (01064CC9h)  
01064CBD  mov         dword ptr [ebp-0E8h],1  
01064CC7  jmp         main+73h (01064CD3h)  
01064CC9  mov         dword ptr [ebp-0E8h],0  
01064CD3  mov         eax,dword ptr [ebp-0E8h]  
01064CD9  mov         dword ptr [test],eax

上面的EAX寄存器应该是存了getchar()的返回值,那后面这个值是怎么样被后续操作抹掉的?我不太懂。

  • 写回答

3条回答 默认 最新

  • yukangliu 2016-09-19 14:41
    关注

    while ((thischar=getchar()) != EOF)
    {

    test = ((thischar = getchar()) != EOF); //Q1.
    这两行代码在你输入1和2时分别被赋值1和2;
    while ((thischar = getchar()) != EOF && flag == 1)
    {
    putchar(thischar);
    这几行代码运行是才是输出后面的赋值3,4 ,5,6,7,8;
    如果需要更改,可改成:

    main()
    {
        int thischar,test=0;
        char flag = 0;
    
        while ((thischar=getchar()) != EOF)
        {   
                putchar(thischar);
            test = ((thischar = getchar()) != EOF);  //Q1.
                    putchar(thischar);
           // printf("The value of condition after putchar(): %d \n", test);
            flag = 1;
            //if ((thischar = getchar()) != EOF);   //test step
            while ((thischar = getchar()) != EOF && flag == 1)
            {
                putchar(thischar);
                //printf("\n");
            }
            flag = 0;
    
        }
    }
    
    

    这样应该可以看明白吧。

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(2条)

报告相同问题?

悬赏问题

  • ¥15 YoloV5 第三方库的版本对照问题
  • ¥15 请完成下列相关问题!
  • ¥15 drone 推送镜像时候 purge: true 推送完毕后没有删除对应的镜像,手动拷贝到服务器执行结果正确在样才能让指令自动执行成功删除对应镜像,如何解决?
  • ¥15 求daily translation(DT)偏差订正方法的代码
  • ¥15 js调用html页面需要隐藏某个按钮
  • ¥15 ads仿真结果在圆图上是怎么读数的
  • ¥20 Cotex M3的调试和程序执行方式是什么样的?
  • ¥20 java项目连接sqlserver时报ssl相关错误
  • ¥15 一道python难题3
  • ¥15 牛顿斯科特系数表表示