【问题标题】:C - inputting correct code but receiving no outputC - 输入正确的代码但没有收到输出
【发布时间】:2014-07-31 20:39:49
【问题描述】:

当我运行以下代码并输入一个句子时,我没有得到任何输出。光标只是转到一个新行。

我直接从书上复制了这个,并仔细检查了它是否有错误(kernighan & ritchie 的第一版 C 编程语言)

#include <stdio.h>
int main()

{
int c,i,nwhite,nother;
int ndigit[10];

nwhite=nother=0;
for(i=0;i<10;++i)
    ndigit[i] = 0;

while (( c=getchar()) != EOF)
    if(c>= '0' && c<= '9')
        ++ndigit[c-'0'];
    else if (c==' ' || c == '\n' || c == '\t')
        ++nwhite;
    else
        ++nother;

printf("digits =");
for( i=0; i<10; ++i)
    printf("%d",ndigit[i]);
printf(", white space = %d, other = %d\n", nwhite,nother);

return 0;
}

【问题讨论】:

  • I copied this straight off the book and double checked it for mistakes 我认为 Kernighan & Ritchie 可能缩进了...
  • "输入一个句子我没有得到任何输出。"你用EOF结束你的句子吗? (取决于操作系统,但 Ctrl+D/Ctrl+Z?)
  • getchar 应该在获取每个字符后自动发送 EOF ......不是吗? :S
  • @user3689367,不,使用CTRL+Z
  • 你不能在 IDE 或调试器下单步执行它吗?我从不只是转储一些代码并期望它能够工作。

标签: c windows codeblocks


【解决方案1】:

由于您正在测试从另一个来源复制的程序,我想您不想更改它,但要理解它。

getchar() 从标准输入中恰好获得 1 个字符,即标准头 &lt;stdio.h&gt; 中名为 stdin 的文件。

标准输入 stdin 被视为文件。
正式地说,文件结尾是一个“标记”而不是一个“字符”。
但是,一般来说,特定的“字符”用于标记文本文件的“文件结束”。
在 Windows 中,“文件结束”标记是字符 CTRL-Z(其 ASCII 码为 26)。
在 Linxu 中,标记是 CTRL-D(其 ASCII 码是 4)。

另一方面,标准输入通常具有以下行为:

  • 等待用户输入字符,直到按下 Intro/Enter 键。

如果用户不按 Enter,则标准输入不会将控制权交还给程序。即使您输入“文件结尾”字符(例如 CTRL-Z)也会发生这种情况。
但是,其他行为也是可能的。
例如,在 Ubuntu 控制台中,我无需等待按下 Enter 键即可识别 CTRL-D。

无论如何,您必须在系统控制台中明确键入文件结束标记
因此,必须自己按下 CTRL-Z(可能后跟 Enter)或 CTRL-D。

关于 ENTER 和 EOF

按 Enter 后,您的程序会测试 EOF,即系统中的“文件结束”标记。
但是,Enter 关键字不会打印“文件结尾”标记,而只会打印“行尾”标记,这对应于标准字符换行符'\n'

因此,如果希望 while() 循环在按下 Intro/Enter 后终止,则必须针对 '\n' 而不是 EOF 进行测试。

观察结果

可以观察到getchar()没有检索字符CTRL-Z,因为CTRL-Z的ASCII码是26,但是getchar()检索的是负值(一般-1)。
这意味着getchar() 将字符 ASCII 26 识别为文件结束标记,然后将其转换为 C 中具有含义的值,由宏 EOF 提供,而不是 26。

我的意思是 EOF 不是 CTRL-Z,然后在假设 ASCII 26 (CTRL-Z) 将被发送到文本文件的情况下,不能天真地发送 EOF

总结一下,我认为阐明“文件结尾”的抽象概念、EOF 的作用以及“标记”和“字符”的区别是很重要的。
(另一个例子:在 Windows 中,“行尾”的“标记”是一对字符 CTRL-M CTRL-J,它不仅是 1 个字符,而且是 2 个)。

引自标准:

getchar 函数从指向的输入流中返回下一个字符 标准输入。如果流处于文件末尾,则设置流的文件结束指示符并 getchar 返回 EOF。如果发生读取错误,则设置流的错误指示符并 getchar 返回 EOF。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-05-05
    • 2017-05-19
    • 2016-03-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多