stl_iterator_base.h
stl_iterator.h
concept是一组合法表达式的集合。在这里,表达式是一个抽象的概念,并不仅指C++中的表达式。
或者说,concept就是一组约束条件。
如果type T满足concept C定义的所有约束条件,那么就说T是C的module。
如果concept C1的所有module都是concept C2的module,那么就说C1是C2的refinement。
偏特化是指对template class或template function作一定程度的特化,特化之后仍然是一个template class或template function。
指明迭代器的类型,共有五种类型的迭代器,即:
input iterator
必须可以拷贝和赋值;
如果ite是input iterator,那么*ite ite++ ++ite必须是合法的表达式;
必须可以比较;
output iterator
forward iterator
bidirectional iterator
random access iterator
都是trival class,没有任何数据成员,也没有任何成员函数。其作用是将iterator划分为五种相应的类别。
继承自input_iterator_tag
继承自forward_iterator_tag
继承自bidirectional_iterator_tag
分别作为五种iterator的基类,以方便定义iterator的associated type,因此自定义的iterator最好继承这些基类,否则必须自己定义iteraotr的五种associated type。
typename _Tp 指定iterator的value_type
typename _Distence 指定iterator的difference_type
iterator_category 为 input_iterator_tag
pointer 为 _Tp*
reference 为 _Tp&
注意,output_iterator是一个class,而不是一个template,因为其iterator_category为output_iterator_tag, value_type, difference_type,pointer,reference均为void,因此也就不需要泛型化。
typename _Tp 指定iterator的value_type
typename _Distence 指定iterator的difference_type
iterator_category 为 forward_iterator_tag
pointer 为 _Tp*
reference 为 _Tp&
typename _Tp 指定iterator的value_type
typename _Distence 指定iterator的difference_type
iterator_category 为 bidirectional_iterator_tag
pointer 为 _Tp*
reference 为 _Tp&
typename _Tp 指定iterator的value_type
typename _Distence 指定iterator的difference_type
iterator_category 为 random_access_iterator_tag
pointer 为 _Tp*
reference 为 _Tp&
typename _Category 指定iterator_category
typename _Tp 指定value_type
typename _Difference 指定difference_type
typename _Pointer 指定pointer,默认值为 _Tp*
typename _Reference 指定reference,默认值为_Tp&
2.6.1 到2.6.5的五个iterator_base,分别提供了五种类型的iterator_base,但其category不能任意指定,pointer和reference也分别固定为value_type*和value_type&,而iterator提供了最大限度的灵活性,可以任意指定五个associated type。
iterator_traits是一个萃取机,它萃取出iterator的associated type。之所以要引入iterator_traits,是由于C++的原生指针也是一种iterator,但是原生指针本身并不支持五种associated type,所以需要使用iterator_traits萃取原生指针的associated type。iterator_traits是萃取原生指针associated type的方法是使用偏特化。
typename _Iterator 需要萃取特性的Iterator
原生指针_Tp*的iterator_category是random_access_iterator_tag,value_type是_Tp,difference_type是ptrdiff_t,pointer是_Tp*,reference是_Tp&。
因为const _Tp*的value_type不应该是const _Tp,而应该是_Tp,因此对const _Tp*提供偏特化。
这三个函数现在已经不在STL标准中了,已经被iterator_traits代替,但是为了与HP STL回溯兼容,保留了这三个函数。
这三个函数的实现方法是:
如果定义了编译器选项__STL_CLASS_PARTIAL_SPECIALIZATION,即编译器支持类的偏特化,那么直接使用iterator_traits来实现。
如果没有定义__STL_CLASS_PARTIAL_SPECIALIZATION,那么无法用iterator_traits来实现,因为iterator_traits本身必须定义了__STL_CLASS_PARTIAL_SPECIALIZATION才会被定义,此时,使用重载的方法来实现,即分别为五种iterator提供重载函数。
返回相应的iterator_base。
返回指向difference_type的指针,因为如果返回difference_type,开销可能比较大。
返回指向value_type的指针,因为如果返回value_type,开销可能比较大。
计算两个iterator的距离,有两个版本:
如果定义了__STL_CLASS_PARTIAL_SPECIALIZATION,则只需要单纯传入两个iterator,就会返回两个iterator的距离。
如果没有定义__STL_CLASS_PARTIAL_SPECIALIZATION,那么还需要传入一个类型为iterator::difference_type的引用,因为此时编译器无法使用iterator_traits<iteraot>::difference_type来确定返回值的类型,必须要调用者传入。
在实现方法上,对于input_iterator和random_access_iterator,采用不同的实现方法,因为random_access_iterator可以直接相减得到difference_type,而input_iterator则必须遍历[iterator1,iterator)并计数。
使iterator前进某个距离n。
在实现上,分别对input_iteraotr bidirectional_iterator random_access_iterator采用不同的实现方法,因为input_iterator只允许n>=0,而bidirectional_iterator允许n<0,random_access_iterator则允许直接相加,无需步进,效率最高。
typename _Container
它是一个output_iterator,使用_Container::value_type为右值向其赋值时会将该值插入到容器尾部。
传入一个容器的引用,返回它的back_insert_iterator。
typename _Container
它是一个output_iterator,使用_Container::value_type为右值向其赋值时会将该值插入到容器头部。
传入一个容器的引用,返回它的front_insert_iterator。
typename _Container
它是一个output_iterator。
初始化时必须指定容器Container和该容器的iteraotr Ite,使用Container的value_type为右值向其赋值时会将该值插入到Ite的前面一个位置,同时Ite下移一位。
传入一个容器的引用,返回它的insert_iterator。
typename _BidirectionalIterator 反转的iterator type
typename _Tp value_type
typename _Reference reference_type
tynename _Distance difference_type