当我尝试从字符串中解析空白分隔的double值时,我发现了这种奇怪的行为,即以循环方式读出字符串。
以下是该计划:
stringstream ss;
string s("1 2 3 4");
double t;
list<double> lis;
for(int j=0; j!=10; ++j){
ss << s;
ss >> t;
lis.push_back(t);
}
for(auto e : lis){
cout << e << " ";
}
这里输出:
1 2 3 41 2 3 41 2 3 41
如果我将尾随空格追加为s= "1 2 3 4 ";
,我会
1 2 3 4 1 2 3 4 1 2
现在问题:
1)如果我不知道字符串s中有多少条目,我如何读入列表中的所有条目?
2)operator<<
我ss << s;
实际上是谁// declarations as before
ss << s;
while(ss >> t){
lis.push_back(t);
}
// output as before
?是否指定循环阅读?
3)我可以更好地解析吗?
谢谢!
这是固定代码(感谢timrau):
1 2 3 4
这会产生:
stringstream
根据需要。 (在处理下一个输入之前,不要忘记通过ss.clear()
清除{{1}} .;))
来自HeywoodFloyd的另一个有用的评论:还可以使用boost / tokenizer“分割”字符串,请参阅this post
答案 0 :(得分:7)
您可以测试>>
的返回值。
while (ss >> t) {
lis.push_back(t);
}
没有指定循环阅读。它是ss << s
将"1 2 3 4"
附加到流的末尾。
在第一轮之前:
""
在第一次ss << s
之后:
"1 2 3 4"
在第一次ss >> t
之后:
" 2 3 4"
第二次ss << s
之后:
" 2 3 41 2 3 4"
如果1 2 3 41 2 3 41 2 3 41
中没有尾随空格,那么很明显为什么会得到s
。
答案 1 :(得分:0)
然后使用s.length()
表示包含未知数量条目的字符串,如果您使用您的方法。
或者,正如timrau所建议的那样,只需初始化一次你的字符串流。
stringstream ss;
string s("1 2 3 4 5 6 7 8");
ss << s;
double t;
list<double> lis;
while (ss >> t) {
lis.push_back(t);
}
for(auto e : lis){
cout << e << " ";
}
答案 2 :(得分:0)
This stackoverflow post包含一个boost tokenizer示例。您可能希望将字符串标记化并以这种方式迭代它。这将解决timrau指出的无尾随空间问题。