我现在正在学习C ++ Primer第4版并使用IO流。当我尝试运行书中的代码(页289)时:
#include <iostream>
#include <string>
using namespace std;
int main()
{
int ival;
// 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()){
cerr << "bad data, try again\n";
cin.clear(istream::failbit);
continue;
}
//ok to process ival
}
}
键入字符串后我遇到了一个无限循环(比如“as”)。那么这段代码有什么问题呢?
答案 0 :(得分:0)
输入字符串时,提取到ival
失败,并设置 failbit 。然后你尽职地尝试清除该位并继续。但那个字符串仍在缓冲区中!所以这个行为会永远重演。
此外,you didn't actually clear the bit; you just set the stream state to failbit。
您需要只调用std::cin.clear()
,然后在继续之前从缓冲区中提取意外数据。
此外, while (cin >> ival, !cin.eof())
是奇数;我没有检查过行为或优先级,但我想你只是写while ((cin >> ival) && !cin.eof())
。
总之,如果这真的是本书中的代码,那么你需要一本更好的书,因为代码在几个严肃的方面是错误的。如果您真的在编写C ++ 14,那么无论如何都需要更新的书,因为Lippman的C ++ Primer在第5版之前甚至没有更新C ++ 11。
答案 1 :(得分:0)
最后通过添加cin.ignore(INT_MAX,'\ n')使其工作。此行是必需的,因为cin.clear()仅在数据保留在缓冲区中时删除错误标志。为了清除缓冲区,需要cin.ignore。
#include <iostream>
#include <string>
using namespace std;
int main()
{
int ival;
// 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()){
cerr << "bad data, try again" << endl;
cin.clear();
cin.ignore(INT_MAX, '\n');
}
//ok to process ival
}
}