我有两段代码。在main()
单独使用时,它们可以正常工作。
vector<int> v;
cout << "Enter sequance of integers "<< "(press q to quit) : ";
istream_iterator<int> start_cin(cin);
istream_iterator<int> end_of_cin;
copy(start_cin,end_of_cin,back_inserter(v));
for ( vector<int>::iterator It = v.begin();It != v.end(); It++ )
cout << *It << "\t";
cout << endl;
和
vector<string> vS;
cout << "Enter three strings : ";
for ( int i = 0; i < 3; i++ )
vS.push_back(*istream_iterator<string>(cin));
ostream_iterator<string> sIt(cout,", ");
copy(vS.begin(),vS.end(),sIt);
cout << endl;
当这两部分一起使用时,即
#include <iostream>
#include <algorithm>
#include <vector>
#include <iterator>
#include <string>
using namespace std;
int main ()
{
// first part
vector<int> v;
cout << "Enter sequance of integers "<< "(press q to quit) : ";
istream_iterator<int> start_cin(cin);
istream_iterator<int> end_of_cin;
copy(start_cin,end_of_cin,back_inserter(v));
for ( vector<int>::iterator It = v.begin();It != v.end(); It++ )
cout << *It << " \t";
cout << endl;
vector<string> vS;
cout << "Enter three strings : ";
for ( int i = 0; i < 3; i++ )
vS.push_back(*istream_iterator<string>(cin));
ostream_iterator<string> sIt(cout,", ");
copy(vS.begin(),vS.end(),sIt);
cout << endl;
return 0;
}
这里第一部分工作但第二部分给出输出:Enter Three Strings : , , ,
。
我想知道这种行为背后的原因是什么?
感谢。
答案 0 :(得分:3)
copy()
完成后cin
将处于无法读取的状态(!cin.good()
),因为读取了“整数”q
失败。这意味着后续的for
循环将无法读取任何内容。
添加:
cin.clear();
cin.ignore(); // To skip the unread "q"
在for
循环之前。
编辑:
如James Kanze所述,请检查"q"
是导致copy()
终止的原因:
...
cin.clear();
string int_read_terminator;
cin >> int_read_terminator;
if ("q" != int_read_terminator)
{
cerr << "Integer copy() failure: " << int_read_terminator << "\n";
}
else
{
...
答案 1 :(得分:0)
您刚遇到input_iterator
的一个问题:它
要求整个文件属于一种类型。有几种方法
解决这个问题;最常见的是插入过滤streambuf
在实际的源和流之间。因此,例如,第一个
当您输入单行时,您的流的一部分应该终止
只是一个'q'
,类似于:
class UntilQStreambuf : public std::streambuf
{
std::streambuf* mySource;
char myBuffer;
bool myIsAtStartOfLine;
protected:
int underflow()
{
int results = mySource->sbumpc();
if ( results == 'q'
&& myIsAtStartOfLine
&& mySource->sgetc() == '\n' ) {
mySource->sbumpc(); // remove terminator line.
results = traits_type::eof();
}
if ( results != traits_type::eof() ) {
myBuffer = results;
setg( &myBuffer, &myBuffer, &myBuffer + 1 );
}
return results;
}
public:
UntilQStreambuf( std::istream& source )
: mySource( source->rdbuf() )
, myIsAtStartOfLine( true )
{
}
};
(我认为boost::iostream
有一些支持可以做到这一点
编写起来非常简单。)然后,您可以为其设置单独的流
使用streambuf
中的std::cin
来读取数字(或
徘徊无论):
std::vector<int>
getNumbers( std::istream& source )
{
UntilQStreambuf localSB( source );
std::istream src( &localSB );
std::vector<int> results( (std::istream_iterator<int>( src )),
(std::istream_iterator<int>()) );
if ( !src.eof() ) {
// Some other error occurred...
}
return results;
}
通过使用单独的流,不会在中设置结束条件 原始流,您可以稍后再继续(也许使用更多 同样的技术)。