赞
踩
目录
3.2 rbegin()和rend()、crbegin()和crend()函数(不支持forward_list容器)
迭代器(iterator):一种访问string对象以及容器中的元素的类型,不必拘泥于迭代器概念本身,或它到底是容器定义的迭代器类型还是一种对象,只需要理解它的操作是用来访问string对象以及容器里的元素的。其类似于指针。
- vector<int> vint;
- vector<int>::iterator iit; //读写类型
- vector<int>::const_iterator icit; //只读类型
- vector<int>::reverse_iterator reit; //反向迭代器
- vector<int>::const_reverse_iterator reit; //反向只读迭代器
迭代器的类型是:
有迭代器的类型同时拥有返回迭代器的成员函数:begin()和end()函数,它们的返回值就是迭代器类型iterator,所以我们可以使用begin()和end()函数来对容器和string对象的元素进行遍历。begin()指向的是容器的第一个元素,比如:vector就是下标为0的元素,end()指向的是最后一个元素的下一个元素,比如:vector里有10个元素,end()就是指向下标为10的元素,注意:这个元素的值是未知的,未定义的,只是用来表示遍历到了头而已。
- vector<int> vint;
- for(auto it=vint.begin();it!=ving.end();it++)
- {
- cout<<*it<<endl;
- }
为什么begin()要指向开头第一个元素,而end()要指向末尾最后一个元素的下一个呢?
因为:方便判断,左闭合范围
begin()==end():意味着容器里没有元素
begin()+1==end():意味着容器里只有一个元素
begin()+1<end():意味着容器里不止一个元素
cbegin()函数和cend()函数是C++11的新标准,与begin()和end()的区别是,cbegin()和cend()返回的是const_iterator类型。就是用来,1.避免在循环体中做出了对元素修改的操作,2.当容器中所储对象是常量,则也只能使用这种类型。
rbegin()和rend()返回的是reverse_iterator类型。同理还有crbegin()和crend()函数。注意:当迭代器是反向迭代器时,对迭代器进行的运算符操作也是反向的,如++操作,会返回指向容器的上一个元素。
*iterator | 获取迭代器所指容器的元素 |
iterator->item | 解引用,获取该元素名为item的成员,等价于(*iterator).item |
++iterator | 下一个元素 |
--iterator | 上一个元素,forward_list不支持此操作 |
iterator1==iterator2 | 判断两个迭代器是否在同一位置 |
iterator1!=iterator2 | 判断两个迭代器是否在同一位置 |
iterator+n | 迭代器向后移n个位置,n必须是整数 |
iterator-n | 迭代器向前移n个位置,n必须是整数 |
iterator+=n | 迭代器向后移n个位置,iterator=iterator+n,n必须是整数 |
iterator-=n | 迭代器向前移n个位置,n必须是整数 |
iterator1-iterator2 | 看iterator1比iterator2领先几个位置,注意,iterator1必须大于iterator2,且返回类型是difference_type |
>、>=、<、<= | 关系运算,比较两个迭代器的前后位置大小 |
注意:迭代器的运算里,没有iterator1+iterator2!!!,没有两个迭代器相加的运算。
头文件:#include<iterator>
插入迭代器:这些迭代器被绑定在一个容器上,可用来向容器插入元素
三种插入迭代器:
1.back_insert_iterator<_container> (_container:如vector<string>):使用back_inserter函数创建一个对容器使用push_back进行插入的迭代器
2.front_insert_iterator<_container> :使用front_inserter函数创建一个对容器使用push_front进行插入的迭代器
3.insert_iterator<_container> :使用inserter函数创建一个使用insert进行插入的迭代器,接受第二个参数,这个参数必须是一个指向给定容器的迭代器。元素会插入到给定迭代器所指向的元素之前,注意:它第二个参数的位置是固定的,不是说在内存里的存储位置固定,是说它会一直指向它所指向的元素。
此迭代器类型为: insert_iterator<_container> (_container:如vector<string>)
注意:只有支持相应操作的容器才能使用对应的迭代器!
示例:
- list<int> lis={1,2,3,4};
- list<int> lis2;
-
- auto it=back_inserter(lis2);
-
- copy(lis.begin(),lis.end(),back_inserter(lis2)); //lis2:1,2,3,4
- copy(lis.begin(),lis.end(),front_inserter(lis2)); //lis2:4,3,2,1
- copy(lis.begin(),lis.end(),inserter(lis2,lis2.begin()); //lis2:1,2,3,4,因为lis2.begin()==lis2.end(),这里也可以看成指向end(),向end()前插入元素
流迭代器:流迭代器被绑定到I/O流上,它会将对应的流当作一个元素序列来处理,可用来遍历所关联的I/O流。
两种流迭代器:
1.istream_iterator<type> itratorname:输入流迭代器,输入流迭代器允许懒惰求值(第一次绑定的时候,标准库不保证迭代器立即从流中读值,标准库只保证在第一次解引用的之前,读取操作已经完成,一般来说,延迟读取和立即读取没有大区别,但是如果有两个绑定了相同流的不同的迭代器,那么他们两个的读取顺序就很重要了)
操作 | 含义 |
istream_iterator<T> in(is); | 将输入流is绑定到in输入流迭代器上,迭代器读取类型为T的值 |
istream_iterator<T> end; | 一个空的输入流可以表示为流的尾后位置,eof。 |
in1 == in2、in1 != in2 | in1和in2必须读取相同类型。若都是尾后迭代器或绑定到相同的输入,两者就相等 |
*in | 读取相应的值 |
++in、in++ | 有效,且遵循前置和后置递增的规则。 |
2.ostream_iterator<type> itratorname:输出流迭代器,输出流迭代器不允许为空,并不允许指向尾后位置。
操作 | 含义 |
ostream_iterator<T> out(os); | out将类型为T的值写到输出流os中 |
ostream_iterator<T> out(os,d); | out将类型为T的值写出到输出流os中,并且每一个类型为T的值它后面都会添加一个字符串d,d是C风格的字符串(字符串字面值常量/指向"/0"的字符数组指针) |
out == val | out和val必须类型相等 |
*out、++out、out++ | 不做任何操作,都返回out本身 |
示例:
- istream_iterator<int> itis(cin);
- istream_iterator<int> end;
- vector<int> vec(itis,end);
- sort(vec.begin(), vec.end());
- ostream_iterator<int> itos(cout);
- copy(vec.begin(), vec.end(), itos);
- //输入:0,2,4,1,3;
- //输出:0,1,2,3,4;
注意:调用泛型算法的时候,如果算法里的迭代器是反向迭代器,那么其返回的迭代器也将是反向迭代器,这意味着后面如果有对这个迭代器的操作,那么将都会按着反向迭代器的操作来进行,这可能会导致预料之外的结果,比如:
- 序列vec:a b c d , e f g
- auto iterator=find(vec.rbegin(),vec.rend(),','); //反向查找第一个出现‘,’的位置
- cout<<string(vec.rbegin(),iterator)<<endl; //输出:gfe,error,因为我的预期结果是efg
- cout<<string(iterator,vec.end())<<endl; //error!因为此时iterator迭代器是反向迭代器,
- //对这个迭代器进行++操作时,是向vec.begin()靠拢的!
- cout<<string(iterator.base(),vec.end())<<endl; //true!base()函数可以将反向迭代器转换为普通迭代器,指向e字符
使用base()函数可以将反向迭代器转换为普通迭代器,但是其位置会有变化,base后的迭代器指向反向迭代器的所指元素的后一个元素(正序后一个)。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。