容器的结构与分类
容器- 结构与分类
- 序列式容器 sequence
- array, c++11 不可扩容
- vector 向后扩容
- deque double-end queue 双端队列,前后均可扩充
- list 双向环状链表
- forward list, c++11 单向链表
- 关联式容器- associative : key-value ,大量的查找动作 底层是rb-tree 高度平衡BST
- set/multiset :value和key是一个东西
- multi 表示set里面的元素可以重复
- map/multimap 每个节点都是k-v
- Multi 表示map里面的元素可以重复
- set/multiset :value和key是一个东西
- 不定序容器 Unordered containers 底层是用hashtable, c++11
- unordered Set / MultiSet
- Unordered map / MultiMap
- Hash table - separate Chaining
- 如何处理碰撞?
- 设计哈希函数解决碰撞冲突
- 放在同一个bucket中,链表 Chaining
- 如果碰撞次数太多,重新打散…
1. array
testArray()......
5.324 ms
array.size()= 500000
array.front()= 6903
array.back()= 7938
array.data()= 0x7ffee249ee48
target ( 0 ~2147483647): 40
found 40
50.366 ms
2. vector
使用namespace区分测试程序
vector 动态扩容:倍增策略 利用率 >= 50%
testVector()......
190.555 ms
vector.size()= 1000000
vector.front()= 16807
vector.back()= 83347
vector.data()= 0x7fc32d400000
vector.capacity()= 1048576
target ( 0 ~2147483647): 5000
::find(): 20.233 ms
found 5000
sort + bsearch: 1671.94 ms
found 5000
3. List
双向循环链表
- 标准库的sort
- 某些容器自己提供了sort,效率要高一些
4. forward_list
- 注意头尾指针的位置
- push_front();
- 标准库提供的find 循序遍历查找
- 本身提供了sort成员函数
slist 是gun-c 提供的非标准库容器
#include <ext/slist>
5. deque
double-end queue
- deque的结构: 分段连续
- deque 是如何扩容的?
- 分段扩容,每段扩容 buffer的大小
- 分段扩容,每段扩容 buffer的大小
stack
使用deque适配成stack,其实是容器适配器
- 不会提供迭代器,因为会破坏容器的性质
queue
使用deque适配成queue,其实是容器适配器
- 不会提供迭代器,因为会破坏容器的性质
multiset
关联式容器
允许插入重复元素
底层由rbtree实现
- 容器提供的find接口比较快,使用了bst的性质
- 关联式容器,查找效率非常高
- 代价是插入时候要保证rbtree的性质,会进行调整
- size 为1000000, 因为允许重复值的出现
multimap
- 模版参数指定两个,一个是key的类型,一个是value的类型
- 标准库提供的模版类 ::pair <>
- Size 为1000000, 允许重复值存在
unordered_multiset
底层是hash table
- 散列函数
- bucket
- load factor 装填因子
unordered_multimap
set
不允许重复元素插入
- 观察容量
map
不允许重复key插入
- 观察容量 1000000?
- 看一下如何插入的,使用的是[] 插入 key不会重复,只有value重复,所以全部放进去了
priority_queue
使用heap实现,建堆算法
容器的结构与分类
都不是通过继承的方式实现的。
一个容器想要使用另一个容器的功能:
- 继承
- 复合 : 整个STL尽量少的使用了继承
- 委托