当前位置: 首页 > news >正文

C++ STL set容器

和 map、multimap 容器不同,使用 set 容器存储的各个键值对,要求键 key 和值 value 必须相等。

举个例子,如下有 2 组键值对数据:

{<'a', 1>, <'b', 2>, <'c', 3>}
{<'a', 'a'>, <'b', 'b'>, <'c', 'c'>}

显然,第一组数据中各键值对的键和值不相等,而第二组中各键值对的键和值对应相等。对于 set 容器来说,只能存储第 2 组键值对,而无法存储第一组键值对。

基于 set 容器的这种特性,当使用 set 容器存储键值对时,只需要为其提供各键值对中的 value 值(也就是 key 的值)即可。仍以存储上面第 2 组键值对为例,只需要为 set 容器提供 {'a','b','c'} ,该容器即可成功将它们存储起来。

通过前面的学习我们知道,map、multimap 容器都会自行根据键的大小对存储的键值对进行排序,set 容器也会如此,只不过 set 容器中各键值对的键 key 和值 value 是相等的,根据 key 排序,也就等价为根据 value 排序。

另外,使用 set 容器存储的各个元素的值必须各不相同。更重要的是,从语法上讲 set 容器并没有强制对存储元素的类型做 const 修饰,即 set 容器中存储的元素的值是可以修改的。但是,C++ 标准为了防止用户修改容器中元素的值,对所有可能会实现此操作的行为做了限制,使得在正常情况下,用户是无法做到修改 set 容器中元素的值的。

对于初学者来说,切勿尝试直接修改 set 容器中已存储元素的值,这很有可能破坏 set 容器中元素的有序性,最正确的修改 set 容器中元素值的做法是:先删除该元素,然后再添加一个修改后的元素。

值得一提的是,set 容器定义于<set>头文件,并位于 std 命名空间中。因此如果想在程序中使用 set 容器,该程序代码应先包含如下语句:

​
#include <set>
using namespace std;
​
注意,第二行代码不是必需的,如果不用,则后续程序中在使用 set 容器时,需手动注明 std 命名空间(强烈建议初学者使用)。


set 容器的类模板定义如下:

template < class T, // 键 key 和值 value 的类型
class Compare = less<T>, // 指定 set 容器内部的排序规则
class Alloc = allocator<T> // 指定分配器对象的类型
> class set;
注意,由于 set 容器存储的各个键值对,其键和值完全相同,也就意味着它们的类型相同,因此 set 容器类模板的定义中,仅有第 1 个参数用于设定存储数据的类型。

对于 set 类模板中的 3 个参数,后 2 个参数自带默认值,且几乎所有场景中只需使用前 2 个参数,第 3 个参数不会用到。

创建C++ set容器的几种方法

常见的创建 set 容器的方法,大致有以下 5 种。

1) 调用默认构造函数,创建空的 set 容器。比如:

std::set<std::string> myset;

如果程序中已经默认指定了 std 命令空间,这里可以省略 std::。

由此就创建好了一个 set 容器,该容器采用默认的std::less<T>规则,会对存储的 string 类型元素做升序排序。注意,由于 set 容器支持随时向内部添加新的元素,因此创建空 set 容器的方法是经常使用的。

2) 除此之外,set 类模板还支持在创建 set 容器的同时,对其进行初始化。例如:

由此即创建好了包含 3 个 string 元素的 myset 容器。由于其采用默认的 std::less<T> 规则,因此其内部存储 string 元素的顺序如下所示:

"http://c.biancheng.net/java/"
"http://c.biancheng.net/python/"
"http://c.biancheng.net/stl/"


3) set 类模板中还提供了拷贝(复制)构造函数,可以实现在创建新 set 容器的同时,将已有 set 容器中存储的所有元素全部复制到新 set 容器中。

例如,在第 2 种方式创建的 myset 容器的基础上,执行如下代码:

std::set<std::string> copyset(myset);
//等同于
//std::set<std::string> copyset = myset

该行代码在创建 copyset 容器的基础上,还会将 myset 容器中存储的所有元素,全部复制给 copyset 容器一份。

另外,C++ 11 标准还为 set 类模板新增了移动构造函数,其功能是实现创建新 set 容器的同时,利用临时的 set 容器为其初始化。比如:

std::set<std::string> myset{"http://c.biancheng.net/java/",
"http://c.biancheng.net/stl/",
"http://c.biancheng.net/python/"};

注意,由于 retSet() 函数的返回值是一个临时 set 容器,因此在初始化 copyset 容器时,其内部调用的是 set 类模板中的移动构造函数,而非拷贝构造函数。

显然,无论是调用复制构造函数还是调用拷贝构造函数,都必须保证这 2 个容器的类型完全一致。


4) 在第 3 种方式的基础上,set 类模板还支持取已有 set 容器中的部分元素,来初始化新 set 容器。例如:

std::set<std::string> myset{ "http://c.biancheng.net/java/",
"http://c.biancheng.net/stl/",
"http://c.biancheng.net/python/" };
std::set<std::string> copyset(++myset.begin(), myset.end());
由此初始化的 copyset 容器,其内部仅存有如下 2 个 string 字符串:

"http://c.biancheng.net/python/"
"http://c.biancheng.net/stl/"


5) 以上几种方式创建的 set 容器,都采用了默认的std::less<T>规则。其实,借助 set 类模板定义中第 2 个参数,我们完全可以手动修改 set 容器中的排序规则。比如:

set<string> retSet() {
std::set<std::string> myset{ "http://c.biancheng.net/java/",
"http://c.biancheng.net/stl/",
"http://c.biancheng.net/python/" };
return myset;
}
std::set<std::string> copyset(retSet());
//或者
//std::set<std::string> copyset = retSet();

C++ STL set容器包含的成员方法

表 1 列出了 set 容器提供的常用成员方法以及各自的功能。
 

表 1 C++ set 容器常用成员方法
成员方法功能
begin()返回指向容器中第一个(注意,是已排好序的第一个)元素的双向迭代器。如果 set 容器用 const 限定,则该方法返回的是 const 类型的双向迭代器。
end()返回指向容器最后一个元素(注意,是已排好序的最后一个)所在位置后一个位置的双向迭代器,通常和 begin() 结合使用。如果 set 容器用 const 限定,则该方法返回的是 const 类型的双向迭代器。
rbegin()返回指向最后一个(注意,是已排好序的最后一个)元素的反向双向迭代器。如果 set 容器用 const 限定,则该方法返回的是 const 类型的反向双向迭代器。
rend()返回指向第一个(注意,是已排好序的第一个)元素所在位置前一个位置的反向双向迭代器。如果 set 容器用 const 限定,则该方法返回的是 const 类型的反向双向迭代器。
cbegin()和 begin() 功能相同,只不过在其基础上,增加了 const 属性,不能用于修改容器内存储的元素值。
cend()和 end() 功能相同,只不过在其基础上,增加了 const 属性,不能用于修改容器内存储的元素值。
crbegin()和 rbegin() 功能相同,只不过在其基础上,增加了 const 属性,不能用于修改容器内存储的元素值。
crend()和 rend() 功能相同,只不过在其基础上,增加了 const 属性,不能用于修改容器内存储的元素值。
find(val)在 set 容器中查找值为 val 的元素,如果成功找到,则返回指向该元素的双向迭代器;反之,则返回和 end() 方法一样的迭代器。另外,如果 set 容器用 const 限定,则该方法返回的是 const 类型的双向迭代器。
lower_bound(val)返回一个指向当前 set 容器中第一个大于或等于 val 的元素的双向迭代器。如果 set 容器用 const 限定,则该方法返回的是 const 类型的双向迭代器。
upper_bound(val)返回一个指向当前 set 容器中第一个大于 val 的元素的迭代器。如果 set 容器用 const 限定,则该方法返回的是 const 类型的双向迭代器。
equal_range(val)该方法返回一个 pair 对象(包含 2 个双向迭代器),其中 pair.first 和 lower_bound() 方法的返回值等价,pair.second 和 upper_bound() 方法的返回值等价。也就是说,该方法将返回一个范围,该范围中包含的值为 val 的元素(set 容器中各个元素是唯一的,因此该范围最多包含一个元素)。
empty()若容器为空,则返回 true;否则 false。
size()返回当前 set 容器中存有元素的个数。
max_size()返回 set 容器所能容纳元素的最大个数,不同的操作系统,其返回值亦不相同。
insert()向 set 容器中插入元素。
erase()删除 set 容器中存储的元素。
swap()交换 2 个 set 容器中存储的所有元素。这意味着,操作的 2 个 set 容器的类型必须相同。
clear()清空 set 容器中所有的元素,即令 set 容器的 size() 为 0。
emplace()在当前 set 容器中的指定位置直接构造新元素。其效果和 insert() 一样,但效率更高。
emplace_hint()在本质上和 emplace() 在 set 容器中构造新元素的方式是一样的,不同之处在于,使用者必须为该方法提供一个指示新元素生成位置的迭代器,并作为该方法的第一个参数。
count(val)在当前 set 容器中,查找值为 val 的元素的个数,并返回。注意,由于 set 容器中各元素的值是唯一的,因此该函数的返回值最大为 1。

相关文章:

C++ STL set容器

和 map、multimap 容器不同&#xff0c;使用 set 容器存储的各个键值对&#xff0c;要求键 key 和值 value 必须相等。 举个例子&#xff0c;如下有 2 组键值对数据&#xff1a; {<a, 1>, <b, 2>, <c, 3>} {<a, a>, <b, b>, <c, c>} 显然&…...

专业课148,总分410+电子科技大学858信号与系统考研经验电子信息与通信

今年专业课148分&#xff0c;总分410顺利被电子科技大学录取&#xff0c;回望这一年复习还有很多不足&#xff0c;总结一下自己的复习经历&#xff0c;希望对大家复习有所帮助。 数学&#xff1a;&#xff08;多动手&#xff0c;多计算&#xff0c;多总结&#xff0c;打好基础…...

密码学:一文读懂非对称加密算法 DH、RSA

文章目录 前言非对称加密算法的由来非对称加密算法的家谱1.基于因子分解难题2.基于离散对数难题 密钥交换算法-DH密钥交换算法-DH的通信模型初始化DH算法密钥对甲方构建DH算法本地密钥乙方构建DH算法本地密钥DH算法加密消息传递 典型非对称加密算法-RSARSA的通信模型RSA特有的的…...

ZooKeeper 实战(二) 命令行操作篇

文章目录 ZooKeeper 实战(二) 命令行操作篇1. 服务端命令1.1. 服务启动1.2. 查看服务1.3. 重启服务1.4. 停止服务 2. 客户端命令2.1. 启动客户端2.2. 查看节点信息查看根节点详情 ls -s /添加一个watch监视器 ls -w /列举出节点的级联节点 ls -R / 2.3. 查看节点状态2.4. 创建节…...

关于在前台应用路由调用子应用

需求 在实际写项目的过程中&#xff0c;关于一些前台的官网首页&#xff0c;会需要在一写特定的路由侠调用子应用的需求&#xff0c;在编写的过程中在公用的方法中&#xff0c;来进行处理&#xff0c;处理思想如下&#xff0c;在特定的.vue文件中&#xff0c; 后端 通过后端…...

Spring学习 Spring事务控制

7.1.事务介绍 7.1.1.什么是事务&#xff1f; 当你需要一次执行多条SQL语句时&#xff0c;可以使用事务。通俗一点说&#xff0c;如果这几条SQL语句全部执行成功&#xff0c;则才对数据库进行一次更新&#xff0c;如果有一条SQL语句执行失败&#xff0c;则这几条SQL语句全部不…...

c++一些使用频率较高的库函数

目录 memset&#xff08;&#xff09; memset&#xff08;&#xff09;接受三个参数&#xff1a; 注意 swap&#xff08;&#xff09; reverse&#xff08;&#xff09; reverse函数接收两个参数&#xff1a; reverse&#xff08;&#xff09;反转整形向量元素顺序示例 …...

【从零开始学技术】Fiddler 抓取 https 请求大全

1.Fiddler代理浏览器设置 注意浏览器代理区别 Chrome/IE浏览器使用的都是系统代理设置 在chrome浏览器的设置中搜索代理&#xff0c;可以看到 打开IE浏览器&#xff0c;选择设置->Internet选项 Firefox浏览器使用的是单独的一套代理系统 在Firefox的代理设置中&#xff0c;我…...

第二百六十四回

文章目录 概念介绍使用方法示例代码 我们在上一章回中介绍了SliverPadding组件相关的内容&#xff0c;本章回中将介绍Sliver综合示例.闲话休提&#xff0c;让我们一起Talk Flutter吧。 概念介绍 我们在前面的章回中介绍了各种Sliver相关的组件&#xff1a;SliverList,SliverGr…...

用Kimi chat识别并整理图片里面的文字

Kimi chat是有OCR功能的&#xff0c;可以识别图片中的文字。 下面这张图片是一本书的注释&#xff0c;里面提到有不少图书&#xff0c;利用Kimi chat就可以轻松完成提取其中图书书名的任务。 先拿一张图片来做实验。Kimichat的回复&#xff1a; 在您提供的文件内容中&#xf…...

驾驭未来:从传统运维到智能化运维的转型之路

随着科技的飞速发展&#xff0c;企业的业务需求也在不断变化。为了满足这些需求&#xff0c;企业的IT架构逐渐向云原生、容器化和微服务化演进。作为支撑企业业务发展的运维人员&#xff0c;我们需要紧跟时代步伐&#xff0c;不断提升自己的技能和认知水平。 在2023年全球运维大…...

LabVIEW在旋转机械故障诊断中的随机共振增强应用

在现代工业自动化领域&#xff0c;准确的故障诊断对于保障机械设备的稳定运行至关重要。传统的故障检测方法往往因噪声干扰而难以捕捉到微弱的故障信号。随着LabVIEW在数据处理和系统集成方面的优势日益凸显&#xff0c;其在旋转机械故障诊断中的应用开始发挥重要作用&#xff…...

尚硅谷大数据技术-数据湖Hudi视频教程-笔记02【核心概念(基本概念、数据写、数据读)】

大数据新风口&#xff1a;Hudi数据湖&#xff08;尚硅谷&Apache Hudi联合出品&#xff09; B站直达&#xff1a;https://www.bilibili.com/video/BV1ue4y1i7na 尚硅谷数据湖Hudi视频教程百度网盘&#xff1a;https://pan.baidu.com/s/1NkPku5Pp-l0gfgoo63hR-Q?pwdyyds阿里…...

鸿蒙(HarmonyOS)应用开发指南

1. 概述 1.1 简介 鸿蒙&#xff08;即 HarmonyOS &#xff0c;开发代号 Ark&#xff0c;正式名称为华为终端鸿蒙智能设备操作系统软件&#xff09;是华为公司自 2012 年以来开发的一款可支持鸿蒙原生应用和兼容 AOSP 应用的分布式操作系统。该系统利用“分布式”技术将手机、电…...

Android 13 辅助屏导航栏不显示问题

问题 在Android 13 上开启辅助屏幕。但是发现辅助屏systemui 导航按 icon没有显示&#xff0c;但是点击对应的区域有作用 分析 可以用 anroid device monitor 工具分析视图 解决 public NavigationBarView(Context context, AttributeSet attrs) {super(context, attrs);…...

【QT】标准对话框

目录 1 概述 2 QFileDialog对话框 1.选择打开一个文件 2.选择打开多个文件 3&#xff0e;选择已有目录 4&#xff0e;选择保存文件名 3 QColorDialog对话框 4 QFontDialog对话框 5 QInputDialog标准输入对话框 1.输入文字 2&#xff0e;输入整数 3&#xff0e;输入…...

微信小程序跳转方式及问题

一、五种跳转方式 1.wx.navigateTo() 保留当前页面&#xff0c;跳转到应用内的某个页面。但是不能跳到 tabbar 页面 通常推荐使用 wx.navigateTo进行跳转&#xff0c;以便返回原页面&#xff0c;以提高加载速度 wx.navigateTo({url: })2.wx.redirectTo() 关闭当前页面&#x…...

Redis实现分布式会话

Redis实现分布式会话 1 什么是分布式会话 1 这是我么之前学过的注册登录模式 2 如果非常多的人访问&#xff0c;因为单台服务器的访问承受能力是有限的&#xff0c;那么我们就想用多态服务器来承担压力 3 一般通过负载均衡的方式来实现&#xff0c;来分担服务器的压力。 4 负…...

AntDesignBlazor示例——暗黑模式

本示例是AntDesign Blazor的入门示例&#xff0c;在学习的同时分享出来&#xff0c;以供新手参考。 示例代码仓库&#xff1a;https://gitee.com/known/BlazorDemo 1. 学习目标 暗黑模式切换查找组件样式覆写组件样式 2. 添加暗黑模式切换组件 1&#xff09;双击打开MainL…...

高通平台开发系列讲解(USB篇)adb function代码分析

文章目录 一、FFS相关动态打印二、代码入口三、ffs_alloc_inst四、ep0、ep1&ep2的注册五、读写过程沉淀、分享、成长,让自己和他人都能有所收获!😄 📢本文主要介绍高通平台USB adb function代码f_fs.c。 一、FFS相关动态打印 目录:msm-4.14/drivers/usb/gadget/fun…...

以下是对华为 HarmonyOS NETX 5属性动画(ArkTS)文档的结构化整理,通过层级标题、表格和代码块提升可读性:

一、属性动画概述NETX 作用&#xff1a;实现组件通用属性的渐变过渡效果&#xff0c;提升用户体验。支持属性&#xff1a;width、height、backgroundColor、opacity、scale、rotate、translate等。注意事项&#xff1a; 布局类属性&#xff08;如宽高&#xff09;变化时&#…...

连锁超市冷库节能解决方案:如何实现超市降本增效

在连锁超市冷库运营中&#xff0c;高能耗、设备损耗快、人工管理低效等问题长期困扰企业。御控冷库节能解决方案通过智能控制化霜、按需化霜、实时监控、故障诊断、自动预警、远程控制开关六大核心技术&#xff0c;实现年省电费15%-60%&#xff0c;且不改动原有装备、安装快捷、…...

Auto-Coder使用GPT-4o完成:在用TabPFN这个模型构建一个预测未来3天涨跌的分类任务

通过akshare库&#xff0c;获取股票数据&#xff0c;并生成TabPFN这个模型 可以识别、处理的格式&#xff0c;写一个完整的预处理示例&#xff0c;并构建一个预测未来 3 天股价涨跌的分类任务 用TabPFN这个模型构建一个预测未来 3 天股价涨跌的分类任务&#xff0c;进行预测并输…...

oracle与MySQL数据库之间数据同步的技术要点

Oracle与MySQL数据库之间的数据同步是一个涉及多个技术要点的复杂任务。由于Oracle和MySQL的架构差异&#xff0c;它们的数据同步要求既要保持数据的准确性和一致性&#xff0c;又要处理好性能问题。以下是一些主要的技术要点&#xff1a; 数据结构差异 数据类型差异&#xff…...

工业自动化时代的精准装配革新:迁移科技3D视觉系统如何重塑机器人定位装配

AI3D视觉的工业赋能者 迁移科技成立于2017年&#xff0c;作为行业领先的3D工业相机及视觉系统供应商&#xff0c;累计完成数亿元融资。其核心技术覆盖硬件设计、算法优化及软件集成&#xff0c;通过稳定、易用、高回报的AI3D视觉系统&#xff0c;为汽车、新能源、金属制造等行…...

JUC笔记(上)-复习 涉及死锁 volatile synchronized CAS 原子操作

一、上下文切换 即使单核CPU也可以进行多线程执行代码&#xff0c;CPU会给每个线程分配CPU时间片来实现这个机制。时间片非常短&#xff0c;所以CPU会不断地切换线程执行&#xff0c;从而让我们感觉多个线程是同时执行的。时间片一般是十几毫秒(ms)。通过时间片分配算法执行。…...

深入解析C++中的extern关键字:跨文件共享变量与函数的终极指南

&#x1f680; C extern 关键字深度解析&#xff1a;跨文件编程的终极指南 &#x1f4c5; 更新时间&#xff1a;2025年6月5日 &#x1f3f7;️ 标签&#xff1a;C | extern关键字 | 多文件编程 | 链接与声明 | 现代C 文章目录 前言&#x1f525;一、extern 是什么&#xff1f;&…...

管理学院权限管理系统开发总结

文章目录 &#x1f393; 管理学院权限管理系统开发总结 - 现代化Web应用实践之路&#x1f4dd; 项目概述&#x1f3d7;️ 技术架构设计后端技术栈前端技术栈 &#x1f4a1; 核心功能特性1. 用户管理模块2. 权限管理系统3. 统计报表功能4. 用户体验优化 &#x1f5c4;️ 数据库设…...

C++.OpenGL (14/64)多光源(Multiple Lights)

多光源(Multiple Lights) 多光源渲染技术概览 #mermaid-svg-3L5e5gGn76TNh7Lq {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg-3L5e5gGn76TNh7Lq .error-icon{fill:#552222;}#mermaid-svg-3L5e5gGn76TNh7Lq .erro…...

DBLP数据库是什么?

DBLP&#xff08;Digital Bibliography & Library Project&#xff09;Computer Science Bibliography是全球著名的计算机科学出版物的开放书目数据库。DBLP所收录的期刊和会议论文质量较高&#xff0c;数据库文献更新速度很快&#xff0c;很好地反映了国际计算机科学学术研…...