STL源码笔记之型别提取技法(2)

2024-05-04 23:32

本文主要是介绍STL源码笔记之型别提取技法(2),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

1.iterator_category

    (1)Input Iterator:这种迭代器所指的对象,不允许外接改变,只读。    

    (2)Output Iterator:只写。

    (3)Forward Iterator:允许“写入型”算法在此迭代器所形成的区间上进行读写操作。

    (4)Bidirectional Iterator:可双向移动。某些算法需要逆向走访某个迭代器区间,可使用Bidirectional Iterator。

    (5)Random Access Iterator:前四种迭代器只提供一部分指针的能力(前三种只支持operator++,operator--),第五种涵盖所有指针算术能力。包括p+n、p-n、p[n]、p1-p2,p1<p2。

      为了能够提供编译迭代器动态选择,STL定义了五种标记用的型别,这样我们在调用涉及到迭代器的函数时,就能选择符合相应迭代器特性的函数。五个迭代器分别为:

                  struct input_iterator_tag{};

                  struct output_iterator_tag{};

                  struct forward_iterator_tag: public input_iterator_tag{};

                  struct bidirection_iterator_tag: public forward_iterator_tag{};

                  struct random_access_iterator_tag: public bidirection_iterator_tag{};

这些class只作标记使用,不占用任何空间。

//advance()为例
//最后一个参数只是用来重载,不需要任何成员
template<class InputIterator,class Distance>
inline void__advance(InputIterator& i,Distance n,input_iterator_tag)
{while(n--)++i;}
template<class ForwardIterator,class Distance>
inline void__advance(ForwardIterator& i,Distance n,forward_iterator_tag)
{
__advance(i,n,input_iterator_tag);
}
template<class BidirectionalIterator,class Distance>
inline void__advance(BidirectionalIterator& i,Distance n,bidirectional_iterator_tag)
{
if(n>=0)while(n--)++i;
else while(n++)--i;
}
template<class RandomAccessIterator,class Distance>
inline void__advance(RandomAccessIterator& i,Distance n,random_access_iterator_tag)
{
i+=n;
}
//调用的时候,InputIterator可以是所有上面的五种迭代器之一
template<class InputIterator,class Distance>
inline void advance(InputIterator& i,Distance n)
{
//自动选择上面的四个函数
//萃取iterator_category必须在每个iterator_traits里面
__advance( i,n,iterator_traits<InputIterator>::iterator_category());
}


2.std::iterator的保证

      为了符合规范,任何迭代器都必须要相应的型别,以利于traits萃取,否则便是自别于整个STL架构,可能无法与STL组件顺利搭配。STL定义了一个标准的iterator class,每个迭代器都继承自它,这样就保证了统一行。

template<
class Category,
class T,
class Distance = ptrdiff_t,
class Pointer = T*,
class Reference = T&              
>
struct iterator{
typedef  Category     iterator_category;
typedef  T                 value_type;
typedef  Distance     difference_type;
typedef  Pointer        pointer;
typedef  Reference   reference  ;
};

      iterator class不含任何成员,纯粹型别定义,所以继承不会招致任何负担,由于后三个参数皆有默认值。故心得迭代器只需要提供两个参数即可。

template<class T>

struct ListIter:public std: iterator<std::forward_iterator_tag,Item>

{...........}

3.__type_traits

      类型粗略的讲有两种,一种是用class封转,并且它的复制拷贝很费时,比如需要深度复制,需要safe copying——即需要调用构造函数完成复制;另一种是所谓的POD(plain old data),一般是build-in类型或是c式的struct类型,这种类型复制和拷贝时只需直接复制内存块就可以了,于是有了bitwise copying或是trival construct/deconstruct/copy/assignment的概念。

      SGI STL中使用__type_traits就可以在编译期间就确定复制一个对象是调用赋值构造函数还是直接调用memcpy,从而提高效率。看SGI STL的源代码:

  1. struct __true_type {};  
  2. struct __false_type {};  
  3.   
  4. template <class type>   //primariy template  
  5. struct __type_traits {   
  6.      typedef __true_type     this_dummy_member_must_be_first;  
  7.       
  8.     typedef __false_type    has_trivial_default_constructor;  
  9.     typedef __false_type    has_trivial_copy_constructor;  
  10.     typedef __false_type    has_trivial_assignment_operator;  
  11.     typedef __false_type    has_trivial_destructor;  
  12.     typedef __false_type    is_POD_type;  
  13. };  
  14. __STL_TEMPLATE_NULL struct __type_traits<char> { //full specialization  
  15.     typedef __true_type    has_trivial_default_constructor;  
  16.     typedef __true_type    has_trivial_copy_constructor;  
  17.      typedef __true_type    has_trivial_assignment_operator;  
  18.     typedef __true_type    has_trivial_destructor;  
  19.     typedef __true_type    is_POD_type;  
  20. };  
  21. __STL_TEMPLATE_NULL struct __type_traits<int> {  
  22.     typedef __true_type    has_trivial_default_constructor;  
  23.     typedef __true_type    has_trivial_copy_constructor;  
  24.     typedef __true_type    has_trivial_assignment_operator;  
  25.     typedef __true_type    has_trivial_destructor;  
  26.     typedef __true_type    is_POD_type;  
  27. };  
接下来,看看怎样使用__type_trairt:
[cpp]  view plain copy
  1. template <class InputIterator, class ForwardIterator, class T>  
  2. inline ForwardIterator __uninitialized_copy(InputIterator first, InputIterator last,  
  3.                      ForwardIterator result, T*) {  
  4.         typedef typename __type_traits<T>::is_POD_type is_POD;  
  5.         return __uninitialized_copy_aux(first, last, result, is_POD());  
  6. }  
  7. template <class InputIterator, class ForwardIterator> inline ForwardIterator   
  8. __uninitialized_copy_aux(InputIterator first, InputIterator last,  
  9.                          ForwardIterator result, __true_type) {  
  10.         return copy(first, last, result); //STL 算法copy里面大有乾坤,针对POD类型,调用memmove,还含有iterator_trait的使用  
  11. }  
  12. template <class InputIterator, class ForwardIterator>  
  13. ForwardIterator __uninitialized_copy_aux(InputIterator first, InputIterator last,  
  14.                          ForwardIterator result, __false_type) {  
  15.         ForwardIterator cur = result;  
  16.         for ( ; first != last; ++first, ++cur)  
  17.                construct(&*cur, *first);  
  18.         return cur;  
  19.   }  
  20. }  

这篇关于STL源码笔记之型别提取技法(2)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/960331

相关文章

Python实现精准提取 PDF中的文本,表格与图片

《Python实现精准提取PDF中的文本,表格与图片》在实际的系统开发中,处理PDF文件不仅限于读取整页文本,还有提取文档中的表格数据,图片或特定区域的内容,下面我们来看看如何使用Python实... 目录安装 python 库提取 PDF 文本内容:获取整页文本与指定区域内容获取页面上的所有文本内容获取

C/C++的OpenCV 进行图像梯度提取的几种实现

《C/C++的OpenCV进行图像梯度提取的几种实现》本文主要介绍了C/C++的OpenCV进行图像梯度提取的实现,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的... 目录预www.chinasem.cn备知识1. 图像加载与预处理2. Sobel 算子计算 X 和 Y

8种快速易用的Python Matplotlib数据可视化方法汇总(附源码)

《8种快速易用的PythonMatplotlib数据可视化方法汇总(附源码)》你是否曾经面对一堆复杂的数据,却不知道如何让它们变得直观易懂?别慌,Python的Matplotlib库是你数据可视化的... 目录引言1. 折线图(Line Plot)——趋势分析2. 柱状图(Bar Chart)——对比分析3

Python对PDF书签进行添加,修改提取和删除操作

《Python对PDF书签进行添加,修改提取和删除操作》PDF书签是PDF文件中的导航工具,通常包含一个标题和一个跳转位置,本教程将详细介绍如何使用Python对PDF文件中的书签进行操作... 目录简介使用工具python 向 PDF 添加书签添加书签添加嵌套书签Python 修改 PDF 书签Pytho

Android实现一键录屏功能(附源码)

《Android实现一键录屏功能(附源码)》在Android5.0及以上版本,系统提供了MediaProjectionAPI,允许应用在用户授权下录制屏幕内容并输出到视频文件,所以本文将基于此实现一个... 目录一、项目介绍二、相关技术与原理三、系统权限与用户授权四、项目架构与流程五、环境配置与依赖六、完整

Android实现定时任务的几种方式汇总(附源码)

《Android实现定时任务的几种方式汇总(附源码)》在Android应用中,定时任务(ScheduledTask)的需求几乎无处不在:从定时刷新数据、定时备份、定时推送通知,到夜间静默下载、循环执行... 目录一、项目介绍1. 背景与意义二、相关基础知识与系统约束三、方案一:Handler.postDel

使用Python从PPT文档中提取图片和图片信息(如坐标、宽度和高度等)

《使用Python从PPT文档中提取图片和图片信息(如坐标、宽度和高度等)》PPT是一种高效的信息展示工具,广泛应用于教育、商务和设计等多个领域,PPT文档中常常包含丰富的图片内容,这些图片不仅提升了... 目录一、引言二、环境与工具三、python 提取PPT背景图片3.1 提取幻灯片背景图片3.2 提取

Python实现word文档内容智能提取以及合成

《Python实现word文档内容智能提取以及合成》这篇文章主要为大家详细介绍了如何使用Python实现从10个左右的docx文档中抽取内容,再调整语言风格后生成新的文档,感兴趣的小伙伴可以了解一下... 目录核心思路技术路径实现步骤阶段一:准备工作阶段二:内容提取 (python 脚本)阶段三:语言风格调

Java 正则表达式URL 匹配与源码全解析

《Java正则表达式URL匹配与源码全解析》在Web应用开发中,我们经常需要对URL进行格式验证,今天我们结合Java的Pattern和Matcher类,深入理解正则表达式在实际应用中... 目录1.正则表达式分解:2. 添加域名匹配 (2)3. 添加路径和查询参数匹配 (3) 4. 最终优化版本5.设计思

一文详解如何在Python中从字符串中提取部分内容

《一文详解如何在Python中从字符串中提取部分内容》:本文主要介绍如何在Python中从字符串中提取部分内容的相关资料,包括使用正则表达式、Pyparsing库、AST(抽象语法树)、字符串操作... 目录前言解决方案方法一:使用正则表达式方法二:使用 Pyparsing方法三:使用 AST方法四:使用字