stringstream
在我调用stringstream::ignore()
时似乎总是失败,即使这是在调用stringstream::clear()
:之后完成的
#include <iostream>
#include <fstream>
#include <sstream>
#include <string>
#include <cassert>
using namespace std;
int main() {
int a, b;
stringstream ss;
string str;
ifstream inFile("file.txt");
if(!inFile) {
cerr << "Fatal: Cannot open input file." << endl;
exit(1);
}
while(getline(inFile, str)) {
ss << str; // read string into ss
ss >> a >> b; // stream fails trying to store string into int
ss.clear(); // reset stream state
assert(ss.good()); // assertion succeeds
ss.ignore(INT_MAX, 'n'); // ignore content to next newline
assert(ss.good()); // assertion fails, why?
}
return 0;
}
file.txt
包含以下文本:
123 abc
456 def
为什么ss.good()
在ss.ignore()
之后为false?
std::endl
输出n
并刷新流。然而,stringstream::flush()
没有任何意义,也没有任何作用。flush
只有当底层缓冲区绑定到像终端这样的输出设备时才有意义,然而,stringstream
没有地方刷新内容。如果你想清除字符串流的内容,请改为ss.str("");
。然而,我可能会将代码更改为以下内容:
while(getline(inFile, str)) {
ss.str(str); // call ss.str() to assign a new string to the stringstream
if(!ss >> a >> b) // check if stream fails trying to store string into int
{
ss.clear(); // Read failed, so reset stream state
}
else
{
// Read successful
}
// Do other stuff
}
此外,如果要在字符串流中插入新行,只需执行ss << 'n';
,而不调用std::endl
。
原来ss
的末尾没有换行符。执行以下语句后:
getline(infile, str);
ss << str;
ss
将不包含换行符,因为getline()
不会将换行符添加到存储在第二个参数中的字符串的末尾。因此,当执行此语句时:
ss.ignore(INT_MAX, 'n');
流失败,因为它到达流的末尾时没有找到要停止的换行符。
如果ss.str()
用于存储字符串,则不需要ss.ignore()
,该字符串将替换流的全部内容如果流失败,则应将其重置,并将其内容设置为空字符串""
。或者,也可以使用ss.ignore()
,但前提是在读取数据后立即将换行符插入流中,以免导致流失败—但是如果稍后使用CCD_ 22将流的内容设置为另一个值
在流被分配文件下一行的内容之前,可以通过调用ss.clear()
来确保成功读取文件的下一行,因为流的旧内容被覆盖在ss.str()
上。流状态可以在循环开始时重置,即使流在循环后期失败,也不会出现问题:
while(getline(inFile, str)) {
ss.clear(); // make sure stream is good
ss.str(str); // overwrite contents of stream with str
ss >> a >> b;
// Even if the stream fails after this line, the stream is reset before each
// line is stored into the stream, and no problems should occur while reading
// and parsing subsequent lines in the file.
// Code to validate and store data from file...
}