针对不同类型迭代器实现各自的高效函数重载
来源:互联网 发布:手机能淘宝开店吗 编辑:程序博客网 时间:2024/05/18 06:05
1.不同的迭代器类型对相同功能的函数需进行不同的处理
1.Input Iterator :只读迭代器,不允许外界改变所指对象
2.Output Iterator:只写迭代器
3.Forward Iterator:单向迭代器,只允许单向移动
4.Bidirectional Iterator:双向迭代器
5.Random Access Iterator:随机访问迭代器(p+n,p-n)
对不同类型的迭代器,处于效率考虑,将采用不同的实现方式。例如对于一个实现迭代器移动的函数,将产生以下几种不同的函数:
①对Input Iterator,Output Iterator,Forward Iterator 类型的迭代器,函数定义如下:
template<class InputIterator,class Distance>void advance_II(InputIterator &iter, Distance n){while (n--) ++iter;}
②对Bidirectional Iterator 类型的迭代器,函数定义如下:
template<class BidirectionIterator,class Distance>void advance_BI(BidirectionIterator & iter, Distance n){if (n > 0)while (n--) ++iter;elsewhile (n++) --iter;}
③对Random_Access Iterator 类型的迭代器,函数定义如下:
template<class RandomAcessIterator ,class Distance>void advance_RAI(RandomAcessIterator &iter, Distance n){iter += n;}
观察上述函数定义,发现对不同类型的函数不能通过重载来进行区分,因为上述函数的参数类型完全相同,所以对其调用提供一个通用接口,根据判断迭代器的类型来决定调用不同的函数:
template<class InputIterator,class Distance>void advance(InputIterator & iter, Distance n){if (is_random_access_iterator(iter)) //is_random_access_iterator 待设计advance_RAT(iter, n);else if (is_bidirection_iterator(iter))advance_BI(iter, n);elseadvance_II(iter, n);}
但是此时也存在缺陷,即对调用哪一个函数,需要到执行期才能决定,会影响程序的效率,我们希望在编译期就能选择正确的版本
前面的三个 advance_xx() 都只有两个函数参数,型别都是未定,为了令这些函数同名,以实现函数重载,我们必须加上一个类型已确定的函数参数。设计思路:如果 traits 有能力萃取出迭代器的种类,则可以用迭代器的类型来作为 advance() 的第三个参数。为了实现在编译期确定正确的函数,则第三个参数必须是类类型,而不能是值。因此,定义以下五个类,代表五种类型迭代器,用来作为迭代器类型的标记
struct input_iterator_tag{};struct output_iterator_tag{};struct forward_iterator_tag : public input_iterator_tag{};struct bidirectional_iterator_tag : public forward_iterator_tag{};struct random_access_iterator_tag : public bidirectional_iterator_tag{};
通过上述迭代器的标记类型引入作为第三个确定参数的方式,我们可以将上述三个函数进行重载,代码如下:
template<class InputIterator, class Distance>void __advance(InputIterator & iter, Distance n,input_iterator_tag){while (n--) ++iter;}template<class BidirectionIterator, class Distance>void __advance(BidirectionIterator & iter, Distance n,bidirectional_iterator_tag){if (n > 0)while (n--) ++iter;elsewhile (n++) --iter;}template<class RandomAcessIterator, class Distance>void __advance(RandomAcessIterator & iter, Distance n,random_access_iterator_tag){iter += n;}
则该函数的公共接口如下,将通过 iterator_traits 对迭代器类型的萃取功能来实现合适的函数调用:
template<class InputIterator, class Distance>void advance(InputIterator& iter, Distance n){__advance(iter, n, iterator_traits<iter>::iterator_category()); //iterator_category()创建一个临时对象,类似:int()}
*注:STL算法的一个命名规则:以算法所能接受的最低阶的迭代器的类型来为其迭代器类别参数命名(如上面的InputIterator)
- 针对不同类型迭代器实现各自的高效函数重载
- 两个不同类型的重载
- 使用重载方法实现不同类型数据的计…
- 两个不同类型的重载“圆”
- vim针对不同类型不同颜色的设置~
- log4j 不同类型分发到各自log文件的设置
- C#方法重载-基于不同类型的参数的方法重载
- 针对重载函数调用运算符的一个使用的例子,也就是重载()这个括号
- memcache的针对不同类型数据应用缓存策略
- 针对不同类型数据的ajax通信方法总结
- 函数重载的实现机制
- JavaScript的重载函数实现
- 函数重载的实现原理
- c函数重载的实现
- c语言重载不同类型数组的print(c99标准)
- C 函数 strstr 的高效实现
- 图像的降采样函数高效实现
- 【C++】用函数模板实现不同类型的两个数比较大小
- 程序员必须知道的10大基础实用算法及其讲解
- /bin/bash^M: bad interpreter: 没有那个文件或目录
- Windows7系统下JAVA运行环境下载、安装和设置
- iperf网络性能测试
- idea 使用maven构建项目
- 针对不同类型迭代器实现各自的高效函数重载
- 前台后台验证 后台像前台编写JavaScript脚本 在控件中添加属性值 母版页以及占位符 内容页
- aop入门前内容:静态代理
- Count and Say
- Qt学习博客
- sg函数
- Multithreading and Grand Central Dispatch on iOS for Beginners Tutorial
- 数据结构之---C语言实现连式多项式
- 《剑指Offer》面试题:对字符串进行循环左移