C++ STL map multimap 查找操作详解
一、容器基础特性
1. map
核心特征
- 关联容器:键值对存储(
key-value
) - 唯一键:每个
key
唯一存在 - 自动排序:按
key
升序排列(默认)
2. multimap
特殊性质
- 允许重复键:同一
key
可对应多个值 - 分组存储:相同
key
的元素连续存放 - 迭代器稳定性:插入/删除不影响已有元素位置
// 典型声明方式
map<int, string> mapStu; // 唯一键容器
multimap<int, string> mumapTeacher; // 允许重复键
二、基础查找操作
1. find()
方法
// map 查找示例
map<int, string>::iterator it = mapStu.find(3);
if (it != mapStu.end()) { // 检查end()cout << "找到元素: " << it->second;
}// multimap 查找相同键
multimap<int, string>::iterator mit = mumapTeacher.find(2022);
特性 | map | multimap |
---|---|---|
返回结果 | 单个迭代器 | 首个匹配迭代器 |
空查找处理 | 返回end() | 返回end() |
2. count()
方法
int num = mumapTeacher.count(2022); // 统计key出现次数
cout << "2022班级教师数量: " << num;
容器 | 返回值范围 | 典型用途 |
---|---|---|
map | 0或1 | 存在性判断 |
multimap | 0到N | 获取重复元素数量 |
三、完整代码解析
#include <iostream>
#include <map>using namespace std;int main() {// map 基础操作map<int, string> mapStu;mapStu.insert(pair<int, string>(3, "李小龙"));mapStu.insert(pair<int, string>(1, "张华")); // 自动排序mapStu.insert(pair<int, string>(4, "庞平"));mapStu.insert(pair<int, string>(2, "任敏"));// map查找演示map<int, string>::iterator it = mapStu.find(3);if (it != mapStu.end()) {cout << "mapStu.find(3) = " << it->second << endl; // ✅ 正确访问方式}// multimap 操作multimap<int, string> mumapTeacher;mumapTeacher.insert(make_pair(2022, "江雪")); // ✅ 推荐使用make_pairmumapTeacher.insert({2022, "薛铃木"}); // C++11初始化列表mumapTeacher.emplace(2023, "林一徹"); // ✅ 高效构造方式mumapTeacher.emplace(2023, "张栗"));// multimap查找方法int count = mumapTeacher.count(2022);multimap<int, string>::iterator mit = mumapTeacher.find(2022);// 方法1:键值判断法for(; mit != mumapTeacher.end(); ++mit) {if(mit->first != 2022) break; // ✅ 安全终止条件cout << mit->second << endl;}// 方法2:计数控制法/*for(int i=0; i<count; ++i, ++mit) { // ⚠️ 需确保迭代器有效cout << mit->second << endl;}*/// equal_range 高级查找auto range = mumapTeacher.equal_range(2022); // C++11自动类型推导for(auto it = range.first; it != range.second; ++it) {cout << "老师: " << it->second << endl;}// 遍历输出for(const auto& elem : mapStu) { // ✅ C++11范围forcout << "Key: " << elem.first << ", Value: " << elem.second << endl;}system("pause");return 0;
}
四、高级查找技巧
1. equal_range()
方法
// 返回包含两个迭代器的pair
auto result = mumapTeacher.equal_range(2023);// 遍历结果范围
for(auto it = result.first; it != result.second; ++it){cout << it->second << endl;
}
返回值成员 | 说明 |
---|---|
first | 指向第一个匹配元素的迭代器 |
second | 指向最后一个匹配元素的下个位置 |
2. 边界安全处理
if(result.first != mumapTeacher.end()) {// 安全处理第一个元素
}if(result.second != mumapTeacher.end()) {// 注意:second可能指向end()
}
五、关键差异对比
特性 | map | multimap |
---|---|---|
键唯一性 | ✅ | ❌ |
operator[] | 支持 | 不支持 |
插入方式 | insert/emplace | insert/emplace |
查找结果 | 单个元素 | 元素范围 |
典型应用场景 | 字典、配置项 | 分组数据、一对多关系 |
六、性能优化建议
-
插入优化
- 预排序数据使用
hint
插入
mapStu.insert(mapStu.end(), {5, "王强"}); // 提示插入位置
- 预排序数据使用
-
查找优化
- 对排序数据使用
lower_bound()/upper_bound()
auto low = mapStu.lower_bound(2); auto high = mapStu.upper_bound(4);
- 对排序数据使用
-
内存管理
- 大量数据时优先使用
unordered_map
(需要哈希支持)
- 大量数据时优先使用
七、常见错误规避
-
未检查迭代器有效性
// 错误示例 cout << mapStu.find(99)->second; // ❌ 可能访问end()// 正确做法 if(auto it = mapStu.find(99); it != mapStu.end()){cout << it->second; }
-
误用operator[]
// multimap不支持[] // mumapTeacher[2022] = "test"; // ❌ 编译错误
-
错误遍历方式
// 错误跳过元素 for(auto it=mit; it!=mumapTeacher.end(); it+=count){...}// 正确应使用equal_range