码:
#include <stdio.h>
#define NEWLINE '\n'
#define SPACE ' '
int main(void)
{
int ch;
int count = 0;
while((ch = getchar()) != EOF)
{
if(ch != NEWLINE && ch != SPACE)
count++;
}
printf("There are %d characters input\n" , count);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
题:
一切正常,它将忽略空格和换行符并输出输入到屏幕的字符数(在这个程序中我只是将逗号,感叹号,数字或任何可打印的特殊符号字符,如&符号作为字符)当我点击EOF模拟是^z.
但是当我将这一行输入程序时出现了问题.例如,我输入:abcdefg^z,这意味着我在同一行之前和之后输入一些字符^z.程序将继续要求输入,而不是终止程序并打印出总字符.
EOF终止字符输入仅在我^z在一行上指定或通过这样做时才起作用:^zabvcjdjsjsj.为什么会这样?
Bri*_*ach 15
几乎每个终端驱动程序都是如此.您将使用Linux获得相同的行为.
你的程序没有实际执行的循环,直至\n或者^z已经被你在一行的末尾输入.终端驱动程序正在缓冲输入,并且在发生之前它尚未发送到您的进程.
在一行结束时,击中^z(或^dLinux上的)不不使终端驱动程序发送EOF.它只会将缓冲区刷新到您的进程(没有\n).
在一行开头命中^z(或^d在Linux上)被终端解释为"我想要发出EOF信号".
如果在循环中添加以下内容,则可以观察到此行为:
printf("%d\n",ch);
Run Code Online (Sandbox Code Playgroud)
运行你的程序:
$ ./test
abc <- type "abc" and hit "enter"
97
98
99
10
abc97 <- type "abc" and hit "^z"
98
99
Run Code Online (Sandbox Code Playgroud)
为了更好地理解这一点,你必须意识到EOF不是一个角色.^z是终端本身的用户命令.因为终端负责接收用户输入并将其传递给进程,所以这变得棘手并因此引起混淆.
一种看待这种情况的方法是点击^v然后点击^z作为你的程序的输入.
^v 是另一个告诉终端的终端命令,"嘿,我输入的下一个东西 - 不要将其解释为终端命令;而是将其传递给进程'输入".