C++中的multiset容器详解
·
C++中的multiset容器详解
1. multiset概述
multiset是C++ STL中的关联容器,允许存储重复的元素,并按照特定排序准则自动排序。它基于红黑树实现,提供高效的查找、插入和删除操作。
2. 基本特性
- 自动排序:元素总是按排序准则排序
- 允许重复:可以存储多个相同值的元素
- 高效操作:查找、插入、删除都是O(log2n)O(\log_2 n)O(log2n)时间复杂度
- 不可修改元素:元素值不可直接修改(会破坏排序)
- 双向迭代器:支持正向和反向遍历
3. 头文件与声明
#include <set> // multiset和set在同一头文件中
using namespace std;
multiset<int> ms1; // 默认升序排列的空multiset
multiset<string, greater<string>> ms2; // 降序排列的multiset
multiset<double> ms3 = {3.14, 2.71}; // 初始化列表
4. 构造函数与初始化
4.1 默认构造
multiset<int> ms;
4.2 比较函数构造
struct CaseInsensitiveCompare {
bool operator()(const string& a, const string& b) const {
return strcasecmp(a.c_str(), b.c_str()) < 0;
}
};
multiset<string, CaseInsensitiveCompare> ms;
4.3 范围构造
int arr[] = {5, 2, 7, 2, 5};
multiset<int> ms(arr, arr+5);
4.4 拷贝构造
multiset<int> ms2(ms1);
5. 容量操作
5.1 size()
cout << ms.size(); // 返回元素数量
5.2 empty()
if(ms.empty()) {
cout << "Multiset is empty";
}
5.3 max_size()
cout << ms.max_size(); // 返回multiset可容纳的最大元素数
6. 元素访问
6.1 迭代器访问
for(auto it = ms.begin(); it != ms.end(); ++it) {
cout << *it << " ";
}
7. 修改操作
7.1 insert()
ms.insert(10); // 插入单个元素
ms.insert({5, 15, 5}); // 插入初始化列表
ms.insert(arr, arr+3); // 插入范围
auto it = ms.insert(20); // 返回指向插入元素的迭代器
7.2 emplace()
ms.emplace(30); // 原地构造元素
7.3 erase()
ms.erase(5); // 删除所有值为5的元素
auto it = ms.find(10);
if(it != ms.end()) {
ms.erase(it); // 删除单个元素
}
ms.erase(ms.begin(), ms.end()); // 删除范围
7.4 clear()
ms.clear(); // 清空所有元素
7.5 swap()
multiset<int> ms2;
ms.swap(ms2); // 交换两个multiset的内容
8. 查找操作
8.1 find()
auto it = ms.find(10); // 返回指向第一个10的迭代器
if(it != ms.end()) {
cout << "Found: " << *it;
}
8.2 count()
cout << ms.count(5); // 返回值为5的元素个数
8.3 lower_bound()
auto it = ms.lower_bound(15); // 返回第一个不小于15的元素
8.4 upper_bound()
auto it = ms.upper_bound(15); // 返回第一个大于15的元素
8.5 equal_range()
auto range = ms.equal_range(5); // 返回等于5的元素范围
for(auto it = range.first; it != range.second; ++it) {
cout << *it << " ";
}
9. 观察器
9.1 key_comp()
auto comp = ms.key_comp();
cout << "Compare 5 and 10: " << comp(5, 10);
9.2 value_comp()
auto comp = ms.value_comp();
cout << "Compare 5 and 10: " << comp(5, 10);
10. 完整示例
#include <iostream>
#include <set>
#include <algorithm>
using namespace std;
int main() {
// 创建并初始化multiset
multiset<int> ms = {5, 2, 8, 2, 5, 10, 5};
// 插入元素
ms.insert(7);
ms.insert({3, 3, 12});
// 遍历multiset (自动排序)
cout << "All elements: ";
for(int num : ms) {
cout << num << " ";
}
cout << endl;
// 查找操作
cout << "Count of 5: " << ms.count(5) << endl;
auto it = ms.find(8);
if(it != ms.end()) {
cout << "Found 8 in multiset" << endl;
}
// 删除操作
ms.erase(2); // 删除所有2
ms.erase(ms.find(5)); // 只删除一个5
// 范围查找
cout << "Elements between 5 and 10: ";
auto low = ms.lower_bound(5);
auto up = ms.upper_bound(10);
for(auto it = low; it != up; ++it) {
cout << *it << " ";
}
cout << endl;
// 相等范围
auto range = ms.equal_range(5);
cout << "All 5s: ";
for(auto it = range.first; it != range.second; ++it) {
cout << *it << " ";
}
cout << endl;
// 容量信息
cout << "Size: " << ms.size() << endl;
cout << "Is empty: " << (ms.empty() ? "Yes" : "No") << endl;
return 0;
}
11. 性能提示
- 插入、删除、查找都是O(log2n)O(\log_2 n)O(log2n)时间复杂度
- 遍历操作是O(n)O(n)O(n)时间复杂度
- 适合需要自动排序且允许重复元素的场景
- 比
unordered_multiset有更好的内存局部性 - 迭代器在插入/删除操作后仍然有效(除非删除的是迭代器指向的元素)
更多推荐

所有评论(0)