- 容器就是某种特定类型的集合。容器之间会提供一些公用的接口,此外没有哪种容器是最优的,只有适合的:
- sequential 容器类型:
- 各个容器的优缺点概览:,其中
array
和forward_list
是新标准添加的。 - 库实现的容器较快,鼓励使用:
- 一些经验之谈,其中
vector
擅长随机访问,list
删除随机增删,如果你不确定后续会进行哪些操作,尽量使用vector
和list
共通的接口: - 尽管容器的元素类型可以是任何类型,但是有些操作会对元素类型有要求。例如某个没有默认构造器的类无法使用只提供元素数量的容器构造器:
- 迭代器是容器访问元素的通用方式:
- 为什么迭代器类型是
left-inclusive ranges
: - 容器中定义的类型成员:
- 惊讶的是,有两个版本的
begin
: - 使用默认构造器是,除了
array
,容器为空,不要以为它初始时会自动预留空间: - 用其他容器来初始化新容器的两种方式:
- 简单认为,array就是内置数组的安全版本:,因为它们的初始化方式都十分相似:
- 容器的关系操作符是建立在元素类型的关系运算符基础上,如果该元素类型不支持关系比较,则容器也不支持:,具体而言就是元素类型的
==
和<
:,注意unordered associative containers
不支持比较运算,相等判断可以。 - 顺序容器涉及的添加元素操作:
push_back
和push_front
只是在容器的两端进行插入,而insert
是更泛化的形式:- push操作会发生拷贝,而
emplace_front()
,emplace()
,emplace_back()
直接在目标内存位置调用元素类型的构造函数: - 对于顺序容器的删除操作,我们需要保证该元素存在:
- 改变容器中元素的数量:
- 对于容器的增删操作会使迭代器、引用和指针失效:,建议的操作是要及时更新相应的迭代器:,例如因为
end()
经常失效,所以应该避免存储end(): - 对于
vector
而言,它的内存是如何增加的:,具体而言,就是想尽办法减少分配内存的操作次数:,容器提供了一些涉及内存容量的接口:,至于capacity()
中过剩容量的具体细节,取决于实现方式: string library
而言,提供一些操作无非就是兼容C风格的字符数组,个人感觉有意思的是子串搜索和匹配操作:- 顺序容器包装的容器适配器:,其中默认情况下: