// read cin and test only for EOF; loop is executed even if there are other IO failures while (cin >> ival, !cin.eof()) { if (cin.bad()) // input stream is corrupted; bail out throw runtime_error("IO stream corrupted");
if (cin.fail()) { // bad input cerr<< "bad data, try again"; // warn the user cin.clear(istream::failbit); // reset the stream continue; // get next input }
// ok to process ival } 这个循环不断读入 cin,直到到达文件结束符或者发生不可恢复的读取错误为止
// remember current state of cin istream::iostate old_state = cin.rdstate(); cin.clear(); process_input(); // use cin cin.clear(old_state); // now reset cin to old state
cout << "hi!" << flush; // flushes the buffer; adds no data cout << "hi!" << ends; // inserts a null, then flushes the buffer cout << "hi!" << endl; // inserts a newline, then flushes the buffer
默认情况下,fstream 对象以 in 和 out 模式同时打开。 当文件同时以 in和 out 打开时不清空。 如果打开 fstream 所关联的文件时,只使用 out 模式,而不指定 in 模式,则文件会清空已存在的数据。 如果打开文件时指定了 trunc模式,则无论是否同时指定了 in 模式,文件同样会被清空。
下面的定义将copyOut 文件同时以输入和输出的模式打开:
// open for input and output fstream inOut("copyOut", fstream::in | fstream::out);
2. 模式是文件的属性而不是流的属性 每次打开文件时都会设置模式
ofstream outfile;
// output mode set to out, "scratchpad" truncated outfile.open("scratchpad", ofstream::out); outfile.close(); // close outfile so we can rebind it
// appends to file named "precious" outfile.open("precious", ofstream::app); outfile.close();
// output mode set by default, "out" truncated outfile.open("out");
第一次调用 open 函数时,指定的模式是 ofstream::out。 当前目录中名为“scratchpad”的文件以输出模式打开并清空。而名为“precious”的文件,则 要求以添加模式打开: 保存文件里的原有数据,所有的新内容在文件尾部写入。 在打开“out”文件时,没有明确指明输出模式,该文件则以 out 模式打开, 这意味着当前存储在“out”文件中的任何数据都将被丢弃。
只要调用 open 函数,就要设置文件模式,其模式的设置可以是显式的也可以是隐式的。 如果没有指定文件模式,将使用默认值。
表 8.4 列出了有效的模式组合及其含义。 表 8.4 文件模式的组合 out 打开文件做写操作,删除文件中已有的数据 out | app 打开文件做写操作,在文件尾写入 out | trunc 与 out 模式相同 in 打开文件做读操作 in | out 打开文件做读、写操作,并定位于文件开头处 in | out | trunc 打开文件做读、写操作,删除文件中已有的数据
上述所有的打开模式组合还可以添加 ate 模式。 对这些模式添加 ate 只会改变文件打开时的初始化定位,在第一次读或写之前,将文件定位于文件末尾处。
// opens in binding it to the given file ifstream& open_file(ifstream &in, const string &file) { in.close(); // close in case it was already open in.clear(); // clear any existing errors
// if the open fails, the stream will be in an invalid state in.open(file.c_str()); // open the file we were given return in; // condition state is good if open succeeded }
由于不清楚流 in 的当前状态,因此首先调用 close 和 clear 将这个流设置为有效状态。 然后尝试打开给定的文件。如果打开失败,流的条件状态将标志这个流是不可用的。 最后返回流对象 in,此时,in 要么已经与指定文件绑定起来了,要么处于错误条件状态。