条款1:仔细选择你的容器
标准STL序列容器:vector、string、deque和list。
标准STL关联容器:set、multiset、map和multimap。
非标准序列容器slist和rope。
非标准关联容器hash_set、hash_multiset、hash_map和hash_multimap。
vector<char>可以作为string的替代品。
vector作为标准关联容器的替代品。
几种标准非STL容器,包括数组、bitset、valarray、stack、queue和priority_queue。
任意位置插入选 序列容器
不关心容器中的位置 散列容器
vector,deque,string 随机迭代器
slist 前向迭代器
插入删除不在意移动元素
连续内存容器
数据内存布局兼容C vector
查找速度敏感 散列容器,排序的vector,标准关联容器
底层使用引用计数 string,rop
需要插入删除事务语义 list(也可在其它连续内存容器实现,开销大)
减少迭代器,指针,引用失效 基于结点的容器
插入在结尾,随机访问迭代器 deque
条款2: 小心对“容器无关代码”的幻想
不要试图写容器无关的代码
改变容器类型的必然性
简单方法是typedef容器类型,迭代器类型,又是简化代码
条款3:使容器里对象的拷贝轻量正确
进入容器的是你指定对象的拷贝。拷贝对象是STL的方式。
简单的方式是建立智能指针的容器而不是对象的容器
条款4:用empty来代替检查size()是否为0,插入删除vs. Size 谁优先?
条款5:尽量使用区间成员函数代替它们的单元素兄弟:简单清楚性能
条款6:警惕C++最令人恼怒的解析
list<int> data(istream_iterator<int>(dataFile), istream_iterator<int>());
构造函数{dy}个参数使用匿名对象,简单办法:使用命名对象
条款7:当使用new得指针的容器时,记得在销毁容器前delete那些指针
条款8:xx建立auto_ptr的容器
可能导致容器中的指针NULL
条款9:在删除选项中仔细选择
去除一个容器中有特定值的所有对象:
vector、string或deque,使用erase-remove惯用法。
list,使用list::remove。
标准关联容器,用erase成员
去除一个容器中满足一个特定判定式的所有对象:
vector、string或deque,使用erase-remove_if惯用法。
list,使用list::remove_if。
标准关联容器,使用remove_copy_if和swap,或遍历,把迭代器传给erase时后置递增。
在循环内做某些事情(除了删除对象之外):
标准序列容器,遍历,当调用erase时用它的返回值更新你的迭代器。
标准关联容器,遍历,当你把迭代器传给erase时记得后置递增它。
条款10:注意分配器的协定和约束
大多数标准容器从未调用它们例示的分配器!!!
把你的分配器做成一个模板,带有模板参数T,代表你要分配内存的对象类型。
提供pointer和reference的typedef,但是总是让pointer是T*,reference是T&。
决不要给你的分配器每对象状态。通常,分配器不能有非静态的数据成员。
记得应该传给分配器的allocate成员函数需要分配的对象个数而不是字节数。也应该记得这些函数返回T*指针(通过pointer typedef),即使还没有T对象被构造。
一定要提供标准容器依赖的内嵌rebind模板。