文件结束符
文件结束符    回车 再ctrl+z 然后再来一次 也就是两次ctrll+z
它才会结束的 我以前也不明白 为什么需要两次ctrl+z才行 人们好像说是一个bug
Windows系统中一般采用阻塞式检查 Ctrl+Z、Unix/Linux系统下一般采用非阻塞式的检查 Ctrl+D。楼主是在Windows系统下,因此使用阻塞式的 Ctrl+Z 来标识流的结束。
这种阻塞式的方式有一个特点:只有按下回车之后才有可能检测在此之前是否有Ctrl+Z按下。还有一个特点就是:如果输入缓冲区中有可读的数据则不会 检测Ctrl+Z(因为有要读的数据,还不能认为到了流的末尾)。还有一点需要知道:Ctrl+Z产生的不是一个普通的ASCII码值,也就是说它产生的 不是一个字符,所以不会跟其它从键盘上输入的字符一样能够存放在输入缓冲区。明白了这几点之后就可以来解释楼主提出的问题了。
从键盘上输入abcd^z 加 回车之后在Windows系统上是这样处理的:由于回车的作用,前面的 abcd 等字符被送到输入 缓冲区(注意:上面说过了,^z不会产生字符,所以更不会存储到输入缓冲区,缓冲区中没有 ^z 的存在)。这时,() 检测 到输入缓冲区中已经有数据存在(因此不再检查是否有 ^z 的输入),于是从缓冲中读取相应的数据。如果都读取完了,则输入缓冲区重新变为空, () 等待新的输入。可见,尽管有 ^z 按下,但是由于在此之前还有其它输入字符(abcd),所以流也不会结束。
因此,输入流结束的条件就是:^z 之前不能有任何字符输入(回车除外),否则 ^z 起不到流结束的作用。
//
请教高手,关于文件结束符Ctrl+Z的问题
vector<string> strvec;
string str;
while(cin>>str)
strvec.push_back(str);
cout<<strvec.size();
如果输入:
hello ^Z world ↙
当读入^Z时不是就应该退出while循环了么??
为什么还要再输入一次:
^Z ↙
才退出循环。
而且输出的strvec的size为2,把^Z也读入strvec了。
为什么while遇到第一个^Z时不退出循环呢??
请教高手
Ctrl+Z只能在换行后才会被识别为EOF
具体原因不知。。。
用CTRL+Z模拟文件终止符时的问题
目的是想在从屏幕读入数据时,测试读入ctrl+Z后程序的反应。却发现了一个搞不明白的问题,代码如下:
#include <iostream>
using namespace std;
void main()
{
int input;
cout<<"before input, current err state is:"<<cin.rdstate()<<endl;
cout<<"please enter the first data"<<endl;
cin>>input;
cout<<"The first data is "<<input<<endl;
cout<<"after input the first data, current err state is:"<<cin.rdstate()<<endl;
}
问题:如果只输入CTRL+Z。为什么第一次输入CTRL+Z时,程序没有反应,只有在第二次输入CTRL+Z时,程序才会运行后终
止。我原本以为,在第一次输入CTRL+Z时,cin>>input会导致f()和cin.fail()为真,就应该输出后继的结果,但不是这样,必须第二次输入CTRL+Z才会输出后继的结果。为什么呢?谢谢各位!
//
前几天看过类似问题 当时看了觉得长知识 就保留了
原来的帖子我不到了 我只是转载
代码如下 
-------------------------------------------------------------- 
int main() 
char ch; 
int count = 0; 
<(ch); 
while (cin.fail()==false) 
cout < <ch; 
count++; 
<(ch); 
cout < <"\n" < <count < <"characters read\n"; 
return 0; 
--------------------------------------------------------- 
Vc++ 6.0控制台模式下(^z在Vc中模拟文件尾) 
为什么输入一串字符加^z后,回车,程序不会结束??!! 
比如输入:abcd^z + 回车 
程序回显 abcd 
按道理 
当读到^z时,检测到了文件尾,cin将eofbit,failbit都设为1 
如果eofbit或failbit设为1,cin.fail则返回true,应该结束程序了,调试中为什么不结束? 
输入:abcd + 回车 
程序回显:abcd + 换行符(看不见),然后等待输入,此时按下^Z + 回车可以 
为什么上一种情况不可以? 
困惑,寻解答,谢谢!! 
答案: 
原因分析如下: 
输入缓冲是行缓冲。当从键盘上输入一串字符并按回车后,这些字符会首先被送到输入缓冲区中存储。每当按下回车键后,() 就会检测 输入缓冲区中是否有了可读的数据。() 还会对键盘上是否有作为流结束标志的 Ctrl+Z 或者 Ctrl+D 键 按下作出检查,其检查的方式有两种:阻塞式以及非阻塞式。 
阻塞式检查方式指的是只有在回车键按下之后才对此前是否有 Ctrl+Z 组合键按下进行检查,非阻塞式样指的是按下 Ctrl+ D 之后立即响应的方式。如果在按 Ctrl+D 之前已经从键盘输入了字符,则 Ctrl+D的作用就相当于回车,即把这些字符送到输 入缓冲区供读取使用,此时Ctrl+D不再起流结束符的作用。如果按 Ctrl+D 之前没有任何键盘输入,则 Ctrl+D 就是流结 束的信号。 
Windows系统中一般采用阻塞式检查 Ctrl+Z、Unix/Linux系统下一般采用非阻塞式的检查 Ctrl+D。楼主是在Windows系统下,因此使用阻塞式的 Ctrl+Z 来标识流的结束。 
这种阻塞式的方式有一个特点:只有按下回车之后才有可能检测在此之前是否有Ctrl+Z按下。还有一个特点就是:如果输入缓冲区中有可读的数据则不会 检测Ctrl+Z(因为有要读的数据,还不能认为到了流的末尾)。还有一点需要知道:Ctrl+Z产生的不是一个普通的ASCII码值,也就是说它产生的 不是一
个字符,所以不会跟其它从键盘上输入的字符一样能够存放在输入缓冲区。明白了这几点之后就可以来解释楼主提出的问题了。 
从键盘上输入abcd^z 加 回车之后在Windows系统上是这样处理的:由于回车的作用,前面的 abcd 等字符被送到输入 缓冲区(注意:上面说过了,^z不会产生字符,所以更不会存储到输入缓冲区,缓冲区中没有 ^z 的存在)。这时,() 检测 到输入缓冲区中已经有数据存在(因此不再检查是否有 ^z 的输入),于是从缓冲中读取相应的数据。如果都读取完了,则输入缓冲区重新变为空, () 等待新的输入。可见,尽管有 ^z 按下,但是由于在此之前还有其它输入字符(abcd),所以流也不会结束。 
因此,输入流结束的条件就是:^z 之前不能有任何字符输入(回车除外),否则 ^z 起不到流结束的作用。 
还有个问题 
如果输入abcd^zabcd 
程序回显 abcd 
并等待输入,也就是^Z后的不再显示了 
----------------------------------------------- 
如果输入缓冲区中有可读的数据则不会检测Ctrl+Z(因为有要读的数据,还不能认为到了流的末尾)。还有一点需要知道:Ctrl+Z产生的不是一个 普通的ASCII码值,也就是说它产生的不是一个字符,所以不会跟其它从键盘上输入的字符一样能够存放在输入缓冲区。 
>> 如果输入abcd^zabcd 
>> 程序回显 abcd 
>> 并等待输入,也就是^Z后的不再显示了 
>> 为什么后面的却没有处理呢? 
所以可以把这种情况下的 ^z 理解为键盘输入的终止,但不是流的终止。
//
非常感谢你的解答,但是我比较了一下你的程序和我的程序,发现如果都是首先就输入ctrl+z,而不输入其他字符,用cin就需要连续两次输入ctrl+z,而()只需要输入一次ctrl+z即可。
也就是说,“输入流结束的条件就是:^z 之前不能有任何字符输入(回车除外),否则 ^z 起不到流结束
的作用。”这句话好像有问题。比如,用cin读入时(在我给出的代码中),即使ctrl+z之前没有任何字符输入,它也起不到流结束的作用。因为,此时仍然需要输入两个ctrl+z,程序才能结束。
非常渴望有人能解答这个问题。
//
我说简单点吗 cin忽略第一个可读数据之(你声明的是int,所以只会读入int)前的所有符号,然后第二个EOF就会是你的cin流错误,使用cin.clear()就可以继续读了。
//
vc++中ctrl+z做文件结束符时怎么不好使?
2009-4-1 17:56
提问者:qiongbian | 悬赏分:30 | 浏览次数:1020次
这个是将任意多个数求和的程序,程序是运行正确的。比方说运行输入时输入:1空格2空格3不空格,ctrl+z,回车,ctrl+z,回车
结果。问题是为什么文件结束符得用两次,有更简便的方法用于表示文件结束的方式或顺序吗?谢谢。
#include<iostream>
int main()
{
std::cout<<"Please enter integrated number:";
int i,num=0;
while(std::cin>>i)
{
num+=i;
}
std::cout<<"The summation is:"<<num<<std::endl;
return 0;
}
2009-4-2 12:49
最佳答案
#include<iostream.h>
void main()
{
cout<<"Please enter integrated number:";
int i,num=0;
()!=EOF)
{
cin>>i;
num+=i;
}
cout<<"The summation is:"<<num<<endl;
}
或者
#include<iostream>
using namespace std;
void main()
{
cout<<"Please enter integrated number:";
int i,num=0;
()!=EOF)
{
cin>>i;
num+=i;
}
cout<<"The summation is:"<<num<<endl;
}
回答者: ljupcn | 八级
擅长领域: 暂未定制
参加的活动: 暂时没有参加的活动
提问者对于答案的评价:
非常感谢啊。果然很好使,我记下了。
神奇的f()
2008年07月17日 星期四 23:53
今天下午一直在看算法导论上的二叉查树,并且立志要下午搞定,想法是好的不过可惜的是这个dev编译器实在是不给面子,简直是不把人摧残到死不罢休的主,唔唔。
要是有本好书,很多东西能很容易的就理解和明白,虽然离熟练还远,但是第一步已经有了,但是在dev中实地操作的时候出现了一个神奇的问题,致使我整个下午都在调试结果还是没有调试出来,后来才发现,问题很有可能出在f()这个函数的身上(虽然到最后我还是没有调试出来)。下面先把我出问题的代码贴出来:
void BuildTree(BST *&T)
{
BST *p;
p = Insert(T);
while(!f())
{Insert(p);}
}
我的本意是在输入流中控制,当程序在键盘缓冲区中读到一个结尾标志后不再调用 Insert() 函数建立2叉树,这样我的2叉树的叶子节点的left,right 2个指针域都是null,根据2叉查树的性质,可以知道,树中的比根的key word大的元素都在根的右子树中,而比根的key word小的元素都在根的左子树中,这样如果我要查一个树中的最大值,只需要取树的最右下的值就可以了,代码如下:
BST * Maxmum(BST *T)
{
BST *max;
max = T;
while(max->right != null)
{ max = max->right; }
return max;
}
这样返回的应该就是树的最大值的节点的指针了,但是在实际的执行过程中始终都不对,在建立的时候,我已经把每个新加的节点的所有指针域都赋成null了,如下:
z->parent = null; z->left = null; z->right = null;  // z 为新加的节点,parent,left,right为节点的3个指针域
所以看来函数从逻辑上是没有任何问题的,于是我在程序中输出了max->right 这个指针域,看其是否为null,结果的确让人意外,max->right 并不是null
,而是一个和之前的元素地址邻接的地址,也就是说程序为我所输入所有元素分配了空间外,还多分配了一个空间,那么是为什么会产生这个分配呢? 原因就是当我在程序中输入完了我希望的所有值以后使用ctrl+z来作为键盘缓冲区的结束标志,但是f()把上一个的enter当作了一次输入,而在下一次的时候才读取了ctrl+z来结束输入,所以会产生一个多余的空间造成程序的错误。解决的办法是在 insert() 函数中加入一个清空键盘缓冲区的语句,这样f()就不会从上一次的输入来读取字符了。
问题总算是解决了,真是拜dev所赐,不仅锻炼了大脑还锻炼了脾胃 。。 一边调试着,一边吐啊吐啊的习惯gcc的调试,恩 很锻炼人。
这个问题总算是解决了,那么继续研究我的2叉查树,明天上的内容就是构建自己的二叉查树~ ^ ^
Have a Good Night ! bye ~
//
为什么f()要按两下ctrol+z
2008-11-7 21:39
提问者:lifeng9891 | 悬赏分:10 | 浏览次数:976次
#include<iostream>
#include<string>
using namespace std;
typedef struct Node
{
string item;
Node *next;
}Node,*PtrNode;
int main()
{
PtrNode p,ptr,Ptr;
Ptr=new Node;
Ptr->next=NULL;
p=Ptr;
while(!f())
{
ptr=new Node;
getline(cin,ptr->item,'\n');
ptr->next=p->next;
p->next=ptr;
p=p->next;
}
return 0;
}
2008-11-7 21:51
最佳答案
Windows系统中一般采用阻塞式检查 Ctrl+Z、Unix/Linux系统下一般采用非阻塞式的检查 Ctrl+D。这种阻塞式的方式有一个特点:只有按下回车之后才有可能检测在此之前是否有Ctrl+Z按下。还有一个特点就是:如果输入缓冲区中有可读的数据则不会检测Ctrl+Z(因为有要读的数据,还不能认为到了流的末尾)。还有一点需要知道:Ctrl+Z产生的不是一个普通的ASCII码值,也就是说它产生的不是一个字符,所以不会跟其它从键盘上输入的字符一样能够存放在输入缓冲区。
//
2006-12-25 18:09
提问者:redberries | 浏览次数:3667次
求f()的用法。书上说它返回输入流结束位,不很理解,谢谢
2006-12-25 20:47
最佳答案
如:
char gc;
while(!f()) //直至按ctrl+z键退出!
{
cin>>gc;
cout<<gc<<endl;
}
回答者: fengjian_net | 八级
擅长领域: 电子数码
参加的活动: 暂时没有参加的活动
提问者对于答案的评价:
linux怎么读取文件内容
thanks
//
f())break;什么意思?C++
2007-6-23 15:25
提问者:c语言啊 | 悬赏分:10 | 浏览次数:1652次
同上  f())break;
cin.clear();又表示什么?
在线等。
2007-6-23 15:30
最佳答案
如:
char gc;
while(!f()) /
/直至按ctrl+z键退出!
{
cin>>gc;
cout<<gc<<endl;
}
cin.clear();是清除标记,回复至初始状态.
//
下面一段程序想着利用cin返回eof状态来结束while语句,但是输入一段字符后强回车并没有退出
2011-3-18 22:39
提问者:thyyks | 浏览次数:392次
#include "stdafx.h"
#include <string>
#include <vector>
#include <iostream>
using namespace std;
int _tmain(int argc, _TCHAR* argv[])
{
vector<string> vecStr;
cout << "input the strings :" << endl;
string strTemp;
while (cin >> strTemp)
vecStr.push_back(strTemp);
cout << "the strings you inputted:" << endl;
for (vector<string>::iterator iteTemp = vecStr.begin();
iteTemp != d(); ++iteTemp)
{
cout << *iteTemp << ends;
}
<();
<();
return 0;
}
2011-3-18 22:54
最佳答案
eof  -- e-End, o-Of, f-File,  是 "End Of File" 文件结束。 EOF 是 文件结束符。
键盘输入 没有 “文件结束”。
有的程序认识 Ctrl-Z, 把 组合键 Ctrl-Z 处理成 eof。
Enter键 是 '\n' , 不是 eof
while (cin >> strTemp)  {}  你可以自己规定输入一个 特殊的字符串 作为结束标志,判断strTemp 等于 这个字符串  时 break; 退出 while.
追问
谢谢的回答,不过根据c++ primer 4th 中提到的eof对于三种流都具有同样的作用,而且我看到在c++ primer 4th的题解中使用到了这种做法
回答
书是人写的,谁都可以写书。书上的东西是否正确,也要通过检验。
你自己写程序试一下吧。
EOF 是 文件结束符。只有你有本领在键盘上打入,EOF,它才能测出。Ctrl-Z 可以产生 EOF,但上次有人说 他/她的编译器编出的程序不能识别。
参加的活动: 暂时没有参加的活动
提问者对于答案的评价:
谢谢了...
c++问题while(cin>>x)怎么用eof结束?
2011-9-13 22:21
提问者:酷暑知了 | 浏览次数:154次
看下面程序,当c是int型时,我输入eof,再回车,退出,但是,我输入e ,即随便输入一个字母,也会退出。当把c改为char型时,输eof会输出0e 0o 0f ;老师说while(cin>>x) 键盘输入eof 退出循环。我用的vs2010,但用同学的C++ sp6试时还是一样?求解!!!!!!!!!
#include "stdafx.h"
//编写一个程序,以十六进制的方式将标准输入的数据直接输出,每行输出25个数字,每个数字之间用一个空格分隔,并用setfill将只有一位数字的十六进制数h以0h的形式输出。(P24课后练习9)
#include <iostream>
#include <iomanip>  //用含参的控制符时 要包含这个
using namespace std ;
int main ()
{
int c ;
int count = 0 ;
cout <<"输入数据 ,摁空格或Tab 输入下一个,摁enter 输出\n"; //连续输入
while ( cin >> c )
{
cout << hex << setw(2)<< setfill ( '0' )<< c;

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。