文章目录
前言
C++ 标准模板库(STL)提供了多种容器类,用于高效地处理各种数据。std::set
是 STL 中的一种关联容器,用于存储唯一的有序元素。它利用平衡二叉树结构(如红黑树)来实现高效的元素查找、插入和删除操作。本文将详细介绍 std::set
的构造函数、成员函数、以及如何使用它。我们还将解释什么是关联容器,并提供示例代码以演示 std::set
的用法。
关联容器概述
关联容器 是 STL 中的一类容器,它们通过某种数据结构(通常是平衡树)来实现高效的元素查找、插入和删除。与顺序容器(如 std::vector
和 std::deque
)不同,关联容器不保证元素的存储顺序,而是按照特定的规则(如排序或哈希)组织元素。常见的关联容器包括 std::set
和 std::map
。
std::set
概述
std::set
是一个关联容器,用于存储唯一的、有序的元素。它的元素按照键值自动排序,且不允许重复。std::set
通过内部的平衡二叉树实现高效的查找、插入和删除操作。
std::set
的构造函数
-
默认构造函数
函数原型:
set();
作用:创建一个空的
std::set
。返回值:无返回值。
示例代码:
std::set<int> s;
-
初始化列表构造函数
函数原型:
set(std::initializer_list<value_type> init, const Compare& comp = Compare(), const Allocator& alloc = Allocator());
作用:使用初始化列表创建
std::set
。参数:
init
:用于初始化std::set
的元素列表。comp
:用于排序的比较器。alloc
:分配器。
返回值:无返回值。
示例代码:
std::set<int> s = {1, 2, 3, 4, 5};
-
拷贝构造函数
函数原型:
set(const set& other);
作用:使用另一个
std::set
对象初始化新对象。新对象将是原对象的副本。参数:
other
:另一个std::set
对象。
返回值:无返回值。
示例代码:
std::set<int> s1 = {1, 2, 3}; std::set<int> s2(s1);
-
移动构造函数
函数原型:
set(set&& other) noexcept;
作用:使用另一个
std::set
对象的资源初始化新对象,并将原对象置于有效但未指定的状态。参数:
other
:另一个std::set
对象(右值)。
返回值:无返回值。
示例代码:
std::set<int> s1 = {1, 2, 3}; std::set<int> s2(std::move(s1));
-
范围构造函数
函数原型:
template <class InputIterator> set(InputIterator first, InputIterator last, const Compare& comp = Compare(), const Allocator& alloc = Allocator());
作用:通过指定范围的迭代器创建
std::set
。参数:
first
:起始迭代器。last
:结束迭代器。comp
:用于排序的比较器。alloc
:分配器。
返回值:无返回值。
示例代码:
std::vector<int> v = {1, 2, 3, 4, 5}; std::set<int> s(v.begin(), v.end());
std::set
的成员函数
1. std::set::insert
函数原型:
std::pair<iterator, bool> insert(const value_type& value);
iterator insert(iterator hint, const value_type& value);
template <class InputIterator>
void insert(InputIterator first, InputIterator last);
作用:插入元素到 std::set
中。如果元素已存在,则插入操作失败。
参数:
value
:要插入的元素。hint
:一个迭代器,用于提示插入的位置(仅用于重载版本)。first
,last
:迭代器范围,用于批量插入(仅用于重载版本)。
返回值:
- 插入成功时,返回一个包含插入位置的迭代器和一个布尔值(表示是否插入成功)。
示例代码:
std::set<int> s;
s.insert(10); // 插入单个元素
s.insert(s.begin(), 20); // 插入元素到指定位置
std::vector<int> v = {30, 40};
s.insert(v.begin(), v.end()); // 批量插入
2. std::set::erase
函数原型:
size_type erase(const value_type& value);
iterator erase(iterator pos);
iterator erase(iterator first, iterator last);
作用:删除指定元素或范围内的元素。
参数:
value
:要删除的元素。pos
:要删除元素的位置。first
,last
:要删除元素的范围。
返回值:
- 删除成功的元素数量(单个元素删除),或删除的迭代器范围(范围删除)。
示例代码:
std::set<int> s = {1, 2, 3, 4, 5};
s.erase(3); // 删除单个元素
s.erase(s.begin()); // 删除指定位置的元素
s.erase(s.begin(), s.end()); // 删除范围内的元素
3. std::set::find
函数原型:
iterator find(const value_type& value);
const_iterator find(const value_type& value) const;
作用:查找 std::set
中是否包含指定的元素。
参数:
value
:要查找的元素。
返回值:指向元素的迭代器。如果未找到,返回 end()
迭代器。
示例代码:
std::set<int> s = {1, 2, 3, 4, 5};
auto it = s.find(3); // 查找元素
if (it != s.end()) {
std::cout << "Element found: " << *it << std::endl;
}
4. std::set::count
函数原型:
size_type count(const value_type& value) const;
作用:返回 std::set
中指定元素的数量。由于 std::set
不允许重复元素,返回值为 0 或 1。
参数:
value
:要计数的元素。
返回值:指定元素的数量(0 或 1)。
示例代码:
std::set<int> s = {1, 2, 3, 4, 5};
std::cout << "Count of 3: " << s.count(3) << std::endl; // 输出 1
std::cout << "Count of 10: " << s.count(10) << std::endl; // 输出 0
5. std::set::clear
函数原型:
void clear();
作用:清空 std::set
中的所有元素。
返回值:无返回值。
示例代码:
std::set<int> s = {1, 2, 3, 4, 5};
s.clear(); // 清空 set
6. std::set::empty
函数原型:
bool empty() const;
作用:检查 std::set
是否为空。
返回值:如果容器为空,返回 true
;否则返回 false
。
示例代码:
std::set<int> s = {1, 2, 3};
if (s.empty()) {
std::cout << "Set is empty." << std::endl;
} else {
std::cout << "Set is not empty." << std::endl;
}
7. std::set::size
函数原型:
size_type size() const;
作用:返回 std::set
中的元素数量。
返回值:容器中元素的数量。
示例代码:
std::set<int> s = {1, 2, 3, 4, 5};
std::cout << "Size of set: " << s.size() << std::endl; // 输出 5
8. std::set::begin
和 std::set::end
函数原型:
iterator begin();
const_iterator begin() const;
iterator end();
const_iterator end() const;
作用:返回指向容器第一个元素和最后一个元素之后的迭代器。
返回值:指向容器第一个元素和最后一个元素之后的迭代器。
示例代码:
std::set<int> s = {1, 2, 3, 4, 5};
for (auto it = s.begin(); it != s.end(); ++it) {
std::cout << *it << " "; // 输出 1 2 3 4 5
}
std::cout << std::endl;
9. std::set::rbegin
和 std::set::rend
函数原型:
reverse_iterator rbegin();
const_reverse_iterator rbegin() const;
reverse_iterator rend();
const_reverse_iterator rend() const;
作用:返回指向容器最后一个元素和第一个元素之前的反向迭代器。
返回值:指向容器最后一个元素和第一个元素之前的反向迭代器。
示例代码:
std::set<int> s = {1, 2, 3, 4, 5};
for (auto rit = s.rbegin(); rit != s.rend(); ++rit) {
std::cout << *rit << " "; // 输出 5 4 3 2 1
}
std::cout << std::endl;
总结
std::set
是一种高效的关联容器,用于存储唯一的、有序的元素。它通过内部的平衡树实现快速的查找、插入和删除操作。std::set
不允许重复元素,且大小在运行时不可调整。了解 std::set
的各种构造函数和成员函数,可以帮助你在需要存储有序且唯一元素的场景中选择合适的容器。