STL六大组件
容器:数据结构,用来存放数据
算法:常用算法
迭代器:容器和算法之间的胶合剂,“范型指针”
仿函数:一种重载了operator()的类,使得这个类的使用看上去像一个函数
配置器:为容器分配并管理内存
适配器:修改其他组件接口
底层为数组,支持随机访问,节点大小是动态的,支持下标访问。随机存取效率很高(O(1)),插入效率不高。
扩容原理:以原大小的两倍配置一份新空间,将原空间数据拷贝过来,会导致迭代器失效
常用函数
size():当前vector元素个数
capacity():vector已分配空间容量
reserve():预分配空间,分配空间小于现有空间,不改变空间容量
resize():改变size大小,不改变容量大小
#include
#include
#include
#include
using namespace std;
void Push(vector<int> &vec,int i){
vec.push_back(i);
cout<<"vector放入"<<i<<"个元素时"<<endl;
cout<<"vec.size()="<<vec.size()<<" vec.capacity()="<<vec.capacity()<<endl;
}
int main(){
vector<int> vec;
cout<<"vector未放入元素时"<<endl;
cout<<"vec.size()="<<vec.size()<<" vec.capacity()="<<vec.capacity()<<endl;
for(int i=1;i<4;i++){
Push(vec,i);
}
cout<<"vec中元素现为"<<endl;
vector<int>::iterator iter=vec.begin();
while(iter!=vec.end()){
cout<<*iter++<<" ";
}
cout<<endl;
vec.resize(2);
cout<<"在vec.resize(2)后"<<endl;
cout<<"vec.size()="<<vec.size()<<" vec.capacity()="<<vec.capacity()<<endl;
cout<<"vec中元素变为"<<endl;
iter=vec.begin();
while(iter!=vec.end()){
cout<<*iter++<<" ";
}
cout<<endl;
vec.reserve(3);
cout<<"在vec.reserve(3)后"<<endl;
cout<<"vec.size()="<<vec.size()<<" vec.capacity()="<<vec.capacity()<<endl;
vec.reserve(5);
cout<<"在vec.reserve(5)后"<<endl;
cout<<"vec.size()="<<vec.size()<<" vec.capacity()="<<vec.capacity()<<endl;
return 0;
}
结果为:
vector未放入元素时
vec.size()=0 vec.capacity()=0
vector放入1个元素时
vec.size()=1 vec.capacity()=1
vector放入2个元素时
vec.size()=2 vec.capacity()=2
vector放入3个元素时
vec.size()=3 vec.capacity()=4
vec中元素现为
1 2 3
在vec.resize(2)后
vec.size()=2 vec.capacity()=4
vec中元素变为
1 2
在vec.reserve(3)后
vec.size()=2 vec.capacity()=4
在vec.reserve(5)后
vec.size()=2 vec.capacity()=5
底层为双向链表,内存空间不连续,只能通过指针访问数据,插入删除高效,随机存取非常没有效率。适用于对象需要大量删除插入操作的环境。
list的iterator不支持+,+=,<操作
list.sort():合并前两个元素,合并后两个元素,两个子序列合并,序列大小变化顺序为2->4->8->16…完成排序(O(log(n)))
双向队列,一个中央控制器+多个缓冲区,支持首尾快速增删,支持随机访问。
底层为deque/list,封闭头部,不使用vector作为底层的原因是vector扩容耗时。
queue:底层为deque/list,封闭头部,不使用vector作为底层的原因是vector扩容耗时。
priority_queue:优先队列,以vector为底层,以heap为处理规则管理底层实现。
有序 | 元素可重复 | |
---|---|---|
set | 是 | 否 |
multiset | 是 | 是 |
map | 是 | 否 |
multimap | 是 | 是 |
插入删除,查找时间复杂度为O(log(n))
作为关联容器,set不同于map的地方在于,set的key就是value。
红黑树的特点:根节点是黑色,叶节点是黑色的null节点,任意节点到其叶节点经过的黑色节点数量是相同的。
去除掉黑色null节点,红黑树是一层黑一层红。
红黑树是近平衡的二叉搜索树,和平衡二叉搜索树相比,红黑树的平衡没有那么平衡,插入后可以保证调整三次之间可以使树达到平衡条件。
有序 | 元素可重复 | |
---|---|---|
hash_set | 否 | 否 |
hash_multiset | 否 | 是 |
hash_map | 否 | 否 |
hash_multimap | 否 | 是 |
查询时间复杂度O(1)
1、扩大每个桶的容量
2、闭地址:桶后增加溢出链
3、开地址;寻找下一个有空间的桶
封装普通指针使其表现的像普通指针一样。超过类的作用域,将会自己调用析构函数,自动释放资源
auto_ptr:不可以用于容器,不建议使用,不支持复制和赋值,如果进行了赋值和复制操作,并不报错
unique_ptr:不支持复制和赋值,直接赋值会报错,同一时刻对象仅能拥有一个unique_ptr指向自身
shared_ptr:解决指针间对象共享所有权的问题,auto_ptr是独享,允许多个指针指向同一个对象。基于引用计数,不要一个原始指针初始化多个shared_ptr,避免循环使用避免内存泄露。
对象初始化时应用数为1,指向对象成为另一个对象副本,引用数加一,析构减一。
weak_ptr:不控制对象生命周期的智能指针,只提供了管理对象的访问手段,用于协助shared_ptr的工作,用于观测资源的使用情况。use_count()可以一观察资源的应用数。