C++ 容器超全讲解
·
目录
vector、list、deque 终极对比(插删效率 + 函数用法)
C++ 容器超全讲解(面试必问 + 上位机开发必用)
我给你用最简单、最实用、不啰嗦、一看就懂的方式讲透 C++ STL 容器。
一、容器是什么?
容器 = 存放数据的工具用来存放:设备数据、配置、列表、临时数据……不用你自己管理内存,超级方便。
二、C++ 容器分 3 大类
1. 顺序容器(按顺序放数据)
vectorlistdeque
2. 关联容器(按 key 查找,快)
mapunordered_mapset
3. 容器适配器(封装后的数据结构)
stackqueue
三、最常用容器 详细说明 + 例子 + 使用场景
1. vector 动态数组(最常用、上位机首选)
特点
- 连续内存
- 随机访问快
- 尾部插入快
- 中间插入慢
用法
cpp
运行
#include <vector>
std::vector<int> data;
data.push_back(10); // 尾部添加
data[0]; // 访问
data.size(); // 大小
使用场景
- 采集数据列表
- 设备列表
- 临时缓存
2. list 双向链表
特点
- 不连续内存
- 任意位置插入、删除快
- 访问慢
使用场景
- 需要频繁插入、删除的数据
3. deque 双端队列
特点
- 头尾插入都快
- 随机访问快
使用场景
- 任务队列
- 数据缓存
4. map 有序键值对(红黑树)
特点
- key 有序
- 查找速度 O (log n)
- 不允许重复 key
用法
cpp
运行
#include <map>
std::map<int, std::string> deviceMap;
deviceMap[1] = "温度传感器";
deviceMap[2] = "PLC";
使用场景
- 设备 ID → 设备名称
- 配置项
5. unordered_map 哈希表(最快)
特点
- 查找速度 O (1)
- 无序
- 最快的键值型容器
使用场景
- 大量数据快速查找
- 设备表、协议解析
6. set 集合(无重复元素)
特点
- 自动去重
- 有序
使用场景
- 设备编号管理
- 不允许重复的数据
7. stack 栈
先进后出
8. queue 队列
先进先出
四、7 个最常用容器 速度对比
表格
| 容器 | 查找 | 尾部插入 | 中间插入 | 优点 |
|---|---|---|---|---|
| vector | 最快 | 快 | 慢 | 通用、最快 |
| list | 慢 | 快 | 最快 | 插入快 |
| map | 快 | - | - | 有序、稳定 |
| unordered_map | 极快 | - | - | 速度最快 |
五、上位机开发 怎么选容器?(黄金规则)
1. 通用列表 → vector
2. 设备 ID 映射 → unordered_map
3. 有序配置 → map
4. 频繁插入删除 → list
5. 任务队列 → queue
六、一句话总结(背会)
vector 万能通用unordered_map 最快查找map 有序查找list 频繁插入删除
七、上位机开发最常用的 3 个
- std::vector
- std::unordered_map
- std::map
vector、list、deque 终极对比(插删效率 + 函数用法)
我给你整理面试必问、工作必用、最清晰的版本,看完永远不混淆!
一、一句话核心区别
- vector:动态数组,连续内存,随机访问快,尾插快,头部 / 中间插删慢
- list:双向链表,不连续内存,任意位置插删都快,访问慢
- deque:双端数组,多段连续内存,头尾插删都快,中间插删慢
二、插删效率大比拼(最重要!)
表格
| 操作 | vector | list | deque |
|---|---|---|---|
| 尾部插入 / 删除 | O (1) 极快 | O (1) 快 | O (1) 极快 |
| 头部插入 / 删除 | O(n) 很慢 | O(1) 极快 | O(1) 极快 |
| 中间插入 / 删除 | O(n) 很慢 | O(1) 极快 | O(n) 很慢 |
| 随机访问 [i] | 最快 | 不支持 | 快 |
| 内存结构 | 连续 | 分散 | 多段连续 |
三、常用函数(完全一样,通用!)
三个容器 90% 函数一模一样,很好记!
通用函数
cpp
运行
push_back(x); // 尾部插入
pop_back(); // 尾部删除
size(); // 元素个数
empty(); // 是否为空
clear(); // 清空
begin(); end(); // 迭代器
front(); back(); // 首尾元素
独有函数
vector
cpp
运行
vec[i]; // 随机访问
capacity(); // 容量
reserve(n); // 预留空间
list
cpp
运行
push_front(x); // 头部插入(快)
pop_front(); // 头部删除(快)
sort(); // 自带排序
remove(x); // 删除所有值为x的元素
unique(); // 去重
deque
cpp
运行
push_front(x); // 头部插入(极快)
pop_front(); // 头部删除(极快)
四、详细用法示例
1. vector(通用首选,尾插最快)
cpp
运行
#include <vector>
vector<int> v;
v.push_back(10); // 尾插
v.pop_back(); // 尾删
v[0]; // 随机访问
v.insert(v.begin()+2, 99); // 中间插(慢)
v.erase(v.begin()); // 头删(慢)
2. list(任意位置插删都快)
cpp
运行
#include <list>
list<int> l;
l.push_back(10); // 尾插
l.push_front(20); // 头插(极快)
l.pop_back(); // 尾删
l.pop_front(); // 头删
l.remove(30); // 删除所有30
// 不支持 [] 访问!
3. deque(双端都快)
cpp
运行
#include <deque>
deque<int> d;
d.push_back(10); // 尾插
d.push_front(20); // 头插(极快)
d.pop_back(); // 尾删
d.pop_front(); // 头删
d[0]; // 支持随机访问
五、最关键:怎么选择?(上位机开发必背)
✅ 用 vector
- 绝大多数场景:设备列表、采集数据、缓存、配置
- 以尾插尾删为主
- 需要快速随机访问
✅ 用 list
- 频繁头尾 / 中间插入、删除
- 消息队列、任务链表
- 不需要随机访问
✅ 用 deque
- 需要头尾都快速插入删除
- 滑动窗口、消费队列、任务队列
六、最强记忆口诀(背会)
vector 连续内存,尾插快、访问快,中间插删慢list 双向链表,任意插删都快,访问慢deque 双端数组,头尾都快,中间慢通用选 vector,频繁插删用 list,双端用 deque
vector / list / map / unordered_map 四种最常用容器,怎么删、效率、注意事项、正确写法。
一、核心结论(先记住)
- vector 删除中间元素:慢(要移动数据)
- list 删除中间元素:快(O (1))
- map /unordered_map 删中间:直接按 key 删
二、vector 删除中间元素
方法:erase (迭代器)
效率:O (n) 慢,因为后面元素要向前移动
cpp
运行
#include <vector>
vector<int> vec = {10,20,30,40,50};
// 删除第 2 个元素(30)
vec.erase(vec.begin() + 2);
// 删除某个值的元素(比如删除 40)
for (auto it = vec.begin(); it != vec.end(); ) {
if (*it == 40)
it = vec.erase(it); // 关键!erase 会返回下一个迭代器
else
++it;
}
✅ 重点:
vector 删除后迭代器会失效,必须接收 erase 返回值!
三、list 删除中间元素
方法:erase (迭代器) 或 remove (val)
效率:O (1) 极快,不移动元素,只需改指针
cpp
运行
#include <list>
list<int> lst = {10,20,30,40,50};
// 方式1:迭代器删除
auto it = lst.begin();
advance(it, 2); // 移动到第 2 个位置
lst.erase(it);
// 方式2:直接删除所有等于 30 的元素
lst.remove(30);
✅ list 最大优势:
删除中间元素最快,不影响其他迭代器!
四、map /unordered_map 删除中间元素
方法:erase (key) 或 erase (迭代器)
效率:map - O (logn),unordered_map - O (1)
cpp
运行
#include <map>
map<int, string> mp;
mp[1] = "PLC";
mp[2] = "传感器";
// 按 key 删除(最常用)
mp.erase(2);
// 按迭代器删除
auto it = mp.find(1);
if (it != mp.end())
mp.erase(it);
五、三种容器删除中间元素 效率对比
表格
| 容器 | 删除中间元素效率 | 特点 |
|---|---|---|
| vector | O (n) 慢 | 移动后面所有元素 |
| list | O (1) 快 | 只需改指针 |
| map | O(logn) | 红黑树 |
| unordered_map | O(1) | 哈希表 |
六、最容易错的地方(面试必问)
❌ 错误写法(迭代器失效)
cpp
运行
// 错误!vector 删完 it 就失效了
for (auto it = vec.begin(); it != vec.end(); ++it) {
if (*it == 30)
vec.erase(it);
}
✅ 正确写法
cpp
运行
for (auto it = vec.begin(); it != vec.end(); ) {
if (*it == 30)
it = vec.erase(it); // 接收返回值
else
++it;
}
七、使用场景总结
- 很少删除中间元素 → vector
- 频繁删除中间元素 → list
- 按 key 快速删除 → unordered_map
八、一句话记忆口诀
vector 删中间慢,要接收迭代器list 删中间最快,随便删map 按 key 删,最方便
更多推荐


所有评论(0)