iostream迭代器

虽然iostream类型不是容器,但标准库定义了可以用于这些IO类型对象的迭代器。

iostream_iterator读取输入流,ostream_iterator向一个输出流写数据。这些迭代器将它们对应的流当作一个特定类型的元素序列来处理,通过使用流迭代器,我们可以用泛型算法从流对象读取数据以及向其中写入数据。

istream_iterator操作

当创建一个流迭代器时,必须指定迭代器将要读写的对象类型,一个istream_iterator使用>>来读取流。因此,istream_iterator要读取的类型必须定义了输入运算符。当创建一个istream_iterator时,我们可以将它绑定到一个流。当然我们还可以默认初始化,这样就建立了一个可以当做尾后迭代器使用的迭代器。
istream_iterator<int> in_iter(cin); // read ints from cin
istream_iterator<int> eof; // istream "end" iterator
ifstream in("afile");
istream_iterator<string> str_it(in);
下面是一个用istream_iterator从标准输入读取数据,存入一个vector的例子。

     istream_iterator<int> in_iter(cin); // read ints from cin
     istream_iterator<int> eof; // istream "end" iterator
     // read until end of file, storing what was read in vec
     while (in_iter != eof)
             // increment advances the stream to the next value
             l// dereference reads next value from the istream
             vec.push_back(*in_iter++);
循环从cin中读取int值,保存在vec中。在每个循环步中,循环体代码检查in_iter是否等于eof。eof被定义为空的istream_iterator,从而可以当作尾后迭代器来使用。对于一个绑定到流的迭代器,一旦关联的流遇到文件尾或遇到io错误迭代器的值就与尾后迭代器相等。

可以将程序改为如下形式

     istream_iterator<int> in_iter(cin); // read ints from cin
     istream_iterator<int> eof;      // istream "end" iterator
     vector<int> vec(in_iter, eof);  // construct vec from an iterator range

iostream迭代器的构造函数

istream_iterator<T> in(strm);

创建从输入流strm中读取T类型对象的istream_iterator对象

istream_iterator<T> in;

istream_iterator 对象的超出末端迭代器

ostream_iterator<T> in(strm);

创建将T类型的对象写到输出流strmostream_iterator对象

ostream_iterator<T> in(strm, delim);

创建将 类型的对象写到输出流 strm ostream_iterator 对象,在写入过程中使用 delim作为元素的分隔符。delim 是以空字符结束的字符数组(C风格字符串)。

istream_iterator 的操作

it1 == it2

it1 != it2

比较两上 istream_iterator 对象是否相等(不等)。迭代器读取的必须是相同的类型。如果两个迭代器都是 end 值,则它们相等。对于两个都不指向流结束位置的迭代器,如果它们使用同一个输入流构造
则它们也相等

*it

返回从流中读取的值

it->mem

是 (*it).mem 的同义词。返回从流中读取的对象的 mem 成员

++it

it++

通过使用元素类型提供的 >> 操作从输入流中读取下一个元素值,使迭代器向前移动。通常,前缀版本使用迭代器在流中向前移动,并返回对加 后的迭代器的引用。而后缀版本使迭代器在流中向前移动后,返回原值


ostream_iterator操作

out =val            用<<运算符将val写入到out所绑定的ostream中,val的类型必须与out可写的类型兼容。

*out ++out out++   这些运算符是存在的,但不对out做任何事,每个运算符都返回out。

我们可以用ostream_iterator来输出值的序列

ostream_iterator<int> out_iter(cout," ");

for(auto e: vec)

*out_iter++=e;

cout<<endl;

此程序将vec中的每个元素写的out,每个元素后加一个空格每次向out_iter赋值时,写操作就会被提交。


值得注意的,当我们向out_iter赋值时,可以忽略解引用和递增运算。因此,可以重写为下面的例子:


for(auto e: vec)

out_iter=e;

cout<<endl;

运算符*和++实际上对ostream_iterator对象不做任何事情,因此忽略它们对我们的程序没有影响。

可以通过调用copy来打印vec中的元素,这比编写循环更为简单

copy(vec.begin(),vec.end(),out_iter);

cout<<endl;

练习题例子

#include<iostream>
#include<vector>
using namespace std;
#include<iterator>

int main()
{
    istream_iterator<int> cin_it(cin);
    istream_iterator<int> end_of_stream;
    vector<int> vec;
    
    while(cin_it!=end_of_stream)
    {
        //注意++先引用后增值,不能写出前缀
        vec.push_back(*cin_it++);
    }
    
    //也可以写成  vector<int> vec(cin_it,end_of_stream);
    for(int i=0;i!=vec.size();i++)
        cout<<vec[i];

    return 0;
}

其中end_of_stream定义为空的迭代器对象,用作结束迭代器。绑定流上的迭代器在遇到文件结束或某个错误时,将等于结束迭代器的值。

int main(int argc, char **argv)
{
    ostream_iterator<string> out_iter(cout, "\n");
    istream_iterator<string> in_iter(cin), EndOfStream;
    while(EndOfStream != in_iter)
    {
        *out_iter++ = *in_iter++; 
    }
    return 0;
}

iter++,返回iter,再*iter

注意输出,输入 12  3 4 5,按 enter输出1 ,2 ,3 ,4,按ctrl+z输出5;

#include "map"
#include "set"
#include "vector"
#include "string"
#include "fstream"
#include "iostream"
#include "sstream"
#include "iterator"
#include "algorithm"
using namespace std;
 
int main(int argc, char **argv)
{
    ifstream infile("C:\\1.txt");
    istream_iterator<int> cin_it(infile);
    istream_iterator<int> EndOfStream;
    vector<int> vec(cin_it, EndOfStream);
    sort(vec.begin(), vec.end());
    ostream_iterator<int> output(cout, " ");
    unique_copy(vec.begin(), vec.end(), output);
    return 0;
}

copy输出的例子

#include <iostream>
#include <algorithm>
#include <iterator>
#include <vector>
using namespace std;

int main()
{
	ostream_iterator<int> intWriter(cout, "\n");
	
	*intWriter = 42;
	intWriter++;
	*intWriter = 77;
	intWriter++;
	*intWriter = -5;
	
	vector<int> coll;
	for(int i = 1; i <= 9; ++i)
	{
		coll.push_back(i);
	}
	
	copy(coll.begin(), coll.end(), ostream_iterator<int>(cout));
	cout << endl;
	
	copy(coll.begin(), coll.end(), ostream_iterator<int>(cout, " < "));
	cout << endl;
	
	return 0;
}

 3)流迭代器的限制

• 不可能从 ostream_iterator 对象读入,也不可能写到istream_iterator 对象中。 

• 一旦给 ostream_iterator 对象赋了一个值,写入就提交了。赋值后,没有办法再改变这个值此外,ostream_iterator 对象中每个不同的值都只能正好输出一次。

• ostream_iterator 没有 -> 操作符。



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值