定义抽象的concepts,并根据抽象的concepts来撰写算法与数据结构,是泛型编程的本质。
运用STL时的几个最重要的观念:
1.所谓使用STL,就是去扩充它。
2.STL的算法和容器是独立分离的。
3.无须继承。
4.抽象化并不意味效率低。
STL所实现的,是依据泛型思维架设起来的一个概念结构。这个以抽象概念为主体而非以实际类为主体的结构,形成了一个严谨的接口标准。在此接口下,任何组件都有最大的独立性,并以所谓迭代器胶合起来,或以所谓配接器互相配接,或以所谓仿函数动态选择某种策略。
六大组件交互关系
Container通过Allocator取得数据储存空间,Algorithm通过Iterator存取Container内容,Functor可以协助Algorithm完成不同的策略变化,Adapter可以修饰或套接Functor。
Iterator
Iterator可说是STL最重要的一个创新发明,它使"将算法与其相关数据结构的关系切割分离“一事变得可能。
何为Concept?
如果Concept既非class,也非function或template,那么它是什么?有三种方式可以了解Concepts,这些方式一开始似乎大不相同,但是最后证明都是相通的。这三种方式有助于了解泛型 算法的一些重要观点。
第一,Concept可以想象是一组型别条件。如果说型别T是Concept C的一个model,则T必 须满足C的所有条件。描述某个型别所必须具备的性质几乎是最容易具体指明Concept的方式了。
第二,Concept可以想成是型别的集合。举例来说,Concept input iterator可涵盖char*、int*、node* 等型别。如果型别T是Concept C 的model,意思便是说T隶属于C所代表的那个型别集合。由于集合中的所有型别都满足那一系列条件,其实是以不同的角度看待同一件事情。
第三,Concept可以想象成是一组合法程序。依次定义,那么像input iterator这样的Concept,其 重要性在于find以及其他许多算法都会用到它。这个Concept自身包含iterator及那些算法共有的 性质。这种定义似乎比前两者更加抽象,但是却很重要,因为就某种意义来说,这是三中方法中 最实用的。这也是新的概念的发掘方法。是的,我们并非藉由写下一组需求条件来发掘和描述新 的概念,而是藉由定义特别的算法并研究模板参数如何运行于这些算法身上的过程来完成。我们 研究find,过程中导出了 input iterator。本书其他各种概念同样是肇因与算法。
Iterator是指针的概括物,它们是”用来指向其他对象“的一种对象。
Iterator对于泛型编程之所以重要,原因是它是算法与数据结构之间的接口。
1、Input Iterator :只允许作为输入,也就是只读(Read Only)
2、Output Iterator :只允许作为输出,也就是只写(Write Only)
3、Forward Iterator :允许读写,但只能做前向移动
4、Bidirectional Iterator :允许读写,可以做双向移动
5、Random Access Iterator :允许读写,可以任意移动,可作(P+N和P-N)、(P[n])、(P1-P2)、(P1 < P2)
Function objects
Function objects是非常一般化的概念,它们可以将任何种类的行为参数化。几乎任何算法都能以“将其行为的某一部分抽象化为function object”的方式来加以一般化。Containers
STL预定义的所有container classes都是一种Forward Container,其中大多数甚至是Bidirectional Container。有一些像block之类的container classes,则属于Random Access Container。
Allocators
很多containers以动态方式分配内存(但非全部如此,例如block就不是)。配置器,它代表一种特定内存模型,并提供一种抽象概念,以便将对内存的申请最终转变为对内存的直接调用。
STL提供了很多泛型容器,如vector,list和map。程序员在使用这些容器时只需关心何时往容器内塞对象,而不用关心如何管理内存,需要用多少内存,这些STL容器极大地方便了C++程序的编写。
Algorithms
各种常用算法,如sort,search,copy,erase。从实现的角度讲,STL算法是一种function template。
Adapters
一种用来修饰容器或仿函数或迭代器接口的东西。
参考:《STL源码剖析》