c++的学习之路:25、map与set

摘要

本文中说一下map与set的使用

目录

摘要

一、关联式容器

二、键值对

三、map

1、map的介绍

2、map的使用

1、map的模板参数说明:

2、map的构造

3、map的迭代器

4、map的容量与元素访问

5、map中元素的修改

6、代码使用

​编辑

三、总结

四、set

1、set的介绍

2、set的使用

1、set的模板参数列表

2、set的构造

3、set的迭代器

4、set的容量

5、set修改操作

6、代码使用

五、multimap

1、multimap的介绍

2、multimap的使用

六、multiset

1、multiset的介绍

2、multiset的使用

七、代码

八、思维导图


一、关联式容器

关联式容器是C++标准模板库(STL)中的一种容器类型,与序列式容器(如vector、list、deque等)不同,关联式容器内部元素的存储和访问是通过关键字(key)进行有序存储的。关联式容器中的元素都是键值对(key,value)结构,并且元素会根据键值按照某种确定的规则自动排序。例如,set、map、multiset和multimap都是关联式容器。

关联式容器的主要特性包括:

1、 有序性:关联式容器中的元素按照键值进行排序。这使得关联式容器在数据检索时比序列式容器效率更高。

2、唯一性:在set和map等容器中,键值是唯一的,这保证了每个元素都能被唯一标识。

3、高效的查找:关联式容器通常使用平衡查找树(如红黑树)或哈希表来实现,这使得它们能在对数时间或常数时间内完成查找操作。

关联式容器的主要操作包括插入、删除和查找等。例如,在unordered_set容器中,可以使用insert方法插入元素,使用find方法查找元素,使用erase方法删除元素。

关联式容器在编程中有很多应用,特别是在需要快速查找、删除和插入元素的场景中。例如,在处理大量数据时,可以使用关联式容器来存储和检索数据,以提高程序的效率。

请注意,关联式容器的选择和使用应根据具体需求进行,不同的关联式容器在性能、功能和用法上可能有所差异。因此,在使用关联式容器时,应仔细考虑其特性和适用场景。

二、键值对

用来表示具有一一对应关系的一种结构,该结构中一般只包含两个成员变量key和value,key代表键值,value表示与key对应的信息。比如:现在要建立一个英汉互译的字典,那该字典中必然有英文单词与其对应的中文含义,而且,英文单词与其中文含义是一一对应的关系,即通过该应该单词,在词典中就可以找到与其对应的中文含义,例如:苹果是apple、香蕉是banana

STL中关于键值对的定义

template <class T1, class T2>
struct pair
{
typedef T1 first_type;
typedef T2 second_type;
T1 first;
T2 second;
pair(): first(T1()), second(T2())
{}
pair(const T1& a, const T2& b): first(a), second(b)
{}
};

三、map

1、map的介绍

下方图片是cplusplus的介绍。翻译过来的意思就是下方六点

1. map是关联容器,它按照特定的次序(按照key来比较)存储由键值key和值value组合而成的元
素。

2. 在map中,键值key通常用于排序和惟一地标识元素,而值value中存储与此键值key关联的内容。键值key和值value的类型可能不同,并且在map的内部,key与value通过成员类型value_type绑定在一起,为其取别名称为pair:typedef pair<const key, T> value_type;

3. 在内部,map中的元素总是按照键值key进行比较排序的。

4. map中通过键值访问单个元素的速度通常比unordered_map容器慢,但map允许根据顺序对元素进行直接迭代(即对map中的元素进行迭代时,可以得到一个有序的序列)。

5. map支持下标访问符,即在[]中放入key,就可以找到与key对应的value。

6. map通常被实现为二叉搜索树(更准确的说:平衡二叉搜索树(红黑树))。

2、map的使用

1、map的模板参数说明:

key: 键值对中key的类型

T: 键值对中value的类型

Compare: 比较器的类型,map中的元素是按照key来比较的,缺省情况下按照小于来比较,一般情况下(内置类型元素)该参数不需要传递,如果无法比较时(自定义类型),需要用户自己显式传递比较规则(一般情况下按照函数指针或者仿函数来传递)

Alloc:通过空间配置器来申请底层空间,不需要用户传递,除非用户不想使用标准库提供的
空间配置器

2、map的构造

函数声明功能介绍
map()构造一个空的map

3、map的迭代器

函数声明功能介绍
begin()和end()begin:首元素的位置,end最后一个元素的下一个位置
cbegin()和cend()与begin和end意义相同,但cbegin和cend所指向的元素不能修改
rbegin()和rend()反向迭代器,rbegin在end位置,rend在begin位置,其++和--操作与begin和end操作移动相反
crbegin()和crend()与rbegin和rend位置相同,操作相同,但crbegin和crend所指向的元素不能修改

4、map的容量与元素访问

函数声明功能简介
bool empty ( ) const检测map中的元素是否为空,是返回true,否则返回false
size_type size() const返回map中有效元素的个数
mapped_type& operator[] (constkey_type& k)返回去key对应的value

5、map中元素的修改

函数声明功能简介
pair<iterator,bool> insert (const value_type& x )在map中插入键值对x,注意x是一个键值对,返回值也是键值对:iterator代表新插入元素的位置,bool代表释放插入成功
void erase ( iterator position )删除position位置上的元素
size_type erase ( const key_type& x )删除键值为x的元素
void erase ( iterator first,iterator last )删除[first, last)区间中的元素
void swap (map<Key,T,Compare,Allocator>&
mp )
交换两个map中的元素
void clear ( )将map中的元素清空
iterator find ( const key_type& x)在map中插入key为x的元素,找到返回该元素的位置的迭代器,否则返回end
const_iterator find ( const key_type& x ) const在map中插入key为x的元素,找到返回该元素的位置的const迭代器,否则返回cend
size_type count ( const key_type& x ) const返回key为x的键值在map中的个数,注意map中key是唯一的,因此该函数的返回值要么为0,要么为1,因此也可以用该函数来检测一个key是否在map中

6、代码使用

下方代码中operator[]的原理是:用<key, T()>构造一个键值对,然后调用insert()函数将该键值对插入到map中, 如果key已经存在,插入失败,insert函数返回该key所在位置的迭代器,如果key不存在,插入成功,insert函数返回新插入元素所在位置的迭代器,operator[]函数最后将insert返回值键值对中的value返回 ,测试结果如图。

void TestMap()
{map<string, string> m;m.insert(pair<string, string>("peach", "桃子"));//构造的时候直接利用pair进行插入m.insert(make_pair("banan", "香蕉"));//利用make_pair函数进行插入m["apple"] = "苹果";//插入+修改  最常用的cout << m.size() << endl;for (auto& e : m)cout << e.first << "--->" << e.second << endl;cout << endl;auto ret = m.insert(make_pair("peach", "桃色"));if (ret.second)cout << "<peach, 桃色>不在map中, 已经插入" << endl;elsecout << "键值为peach的元素已经存在:" << ret.first->first << "--->"<< ret.first->second << " 插入失败" << endl;m.erase("apple");if (1 == m.count("apple"))cout << "apple还在" << endl;elsecout << "apple被吃了" << endl;
}

三、总结

这里是有下面6点:

1、map中的的元素是键值对

2、map中的key是唯一的,并且不能修改

3、默认按照小于的方式对key进行比较

4、map中的元素如果用迭代器去遍历,可以得到一个有序的序列

5、map的底层为平衡搜索树(红黑树),查找效率比较高$O(log_2 N)$

6、支持[]操作符,operator[]中实际进行插入查找。 

四、set

1、set的介绍

下方图片是cplusplus的介绍。翻译过来的意思就是下方五点

1、set是按照一定次序存储元素的容器

2、在set中,元素的value也标识它(value就是key,类型为T),并且每个value必须是唯一的。set中的元素不能在容器中修改(元素总是const),但是可以从容器中插入或删除它们。

3、在内部,set中的元素总是按照其内部比较对象(类型比较)所指示的特定严格弱排序准则进行
排序。

4、set容器通过key访问单个元素的速度通常比unordered_set容器慢,但它们允许根据顺序对
子集进行直接迭代。

5、set在底层是用二叉搜索树(红黑树)实现的。

 有下面8点需要注意注意:

1、与map/multimap不同,map/multimap中存储的是真正的键值对<key, value>,set中只放value,但在底层实际存放的是由<value, value>构成的键值对。

2、set中插入元素时,只需要插入value即可,不需要构造键值对。

3、set中的元素不可以重复(因此可以使用set进行去重)。

4、使用set的迭代器遍历set中的元素,可以得到有序序列

5、set中的元素默认按照小于来比较

6、set中查找某个元素,时间复杂度为:$log_2 n$

7、set中的元素不允许修改

8、set中的底层使用二叉搜索树(红黑树)来实现。

2、set的使用

1、set的模板参数列表

T: set中存放元素的类型,实际在底层存储<value, value>的键值对。

Compare:set中元素默认按照小于来比较

Alloc:set中元素空间的管理方式,使用STL提供的空间配置器管理

2、set的构造

函数声明功能介绍
set (const Compare& comp = Compare(), const Allocator&= Allocator() );构造空的set
set (InputIterator first, InputIterator last, const Compare& comp = Compare(), const Allocator& =Allocator() );用[first,last)区间中的元素构造set
set ( const set<Key,Compare,Allocator>& x);set的拷贝构造

3、set的迭代器

函数声明功能介绍
iterator begin()返回set中起始位置元素的迭代器
iterator end()返回set中最后一个元素后面的迭代器
const_iterator cbegin() const返回set中起始位置元素的const迭代器
const_iterator cend() const返回set中最后一个元素后面的const迭代器
reverse_iterator rbegin()返回set第一个元素的反向迭代器,即end
reverse_iterator rend()返回set最后一个元素下一个位置的反向迭代器,即rbegin
const_reverse_iterator crbegin() const返回set第一个元素的反向const迭代器,即cend
const_reverse_iterator crend() const返回set最后一个元素下一个位置的反向const迭代器,即crbegin

4、set的容量

函数声明功能介绍
bool empty ( ) const检测set是否为空,空返回true,否则返回true
size_type size() const返回set中有效元素的个数

5、set修改操作

函数声明功能介绍
pair<iterator,bool> insert (const value_type& x )在set中插入元素x,实际插入的是<x, x>构成的键值对,如果插入成功,返回<该元素在set中的位置,true>,如果插入失败,说明x在set中已经存在,返回<x在set中的位置,false>
void erase ( iterator position )删除set中position位置上的元素
size_type erase ( const key_type& x )删除set中值为x的元素,返回删除的元素的个数
void erase ( iterator first,iterator last )删除set中[first, last)区间中的元素
void swap (set<Key,Compare,Allocator>&st );交换set中的元素
void clear ( )将set中的元素清空
iterator find ( const key_type& x ) const返回set中值为x的元素的位置
size_type count ( const key_type& x ) const返回set中值为x的元素的个数

6、代码使用

下面代码就是创建个数组,然后进行插入测试,因为set具有去重与排序的功能,如下图测试结果可以看出来

void TestSet()
{int arr[] = { 1, 3, 5, 7, 9, 2, 4, 6, 8, 0, 1, 3, 5, 7, 9, 2, 4, 6, 8, 0 };set<int> s;for (int i = 0; i < sizeof(arr) / sizeof(arr[0]); i++)s.insert(arr[i]);cout << s.size() << endl;for (auto& e : s)cout << e << " ";cout << endl;for (auto it = s.rbegin(); it != s.rend(); ++it)cout << *it << " ";cout << endl;cout << s.count(3) << endl;
}

五、multimap

1、multimap的介绍

下方图片是cplusplus的介绍。翻译过来的意思就是下方五点

1. Multimaps是关联式容器,它按照特定的顺序,存储由key和value映射成的键值对<key,value>,其中多个键值对之间的key是可以重复的。

2. 在multimap中,通常按照key排序和惟一地标识元素,而映射的value存储与key关联的内容。key和value的类型可能不同,通过multimap内部的成员类型value_type组合在一起,value_type是组合key和value的键值对:typedef pair<const Key, T> value_type;

3. 在内部,multimap中的元素总是通过其内部比较对象,按照指定的特定严格弱排序标准对key进行排序的。

4. multimap通过key访问单个元素的速度通常比unordered_multimap容器慢,但是使用迭代器直接遍历multimap中的元素可以得到关于key有序的序列。

5. multimap在底层用二叉搜索树(红黑树)来实现。

注意:multimap和map的唯一不同就是:map中的key是唯一的,而multimap中key是可以重复的。

2、multimap的使用

multimap中的接口可以参考map,功能都是类似的,这里就不具体演示了

注意:

1. multimap中的key是可以重复的。

2. multimap中的元素默认将key按照小于来比较

3. multimap中没有重载operator[]操作(同学们可思考下为什么?)。

4. 使用时与map包含的头文件相同

六、multiset

1、multiset的介绍

下方图片是cplusplus的介绍。翻译过来的意思就是下方五点:

1. multiset是按照特定顺序存储元素的容器,其中元素是可以重复的。

2. 在multiset中,元素的value也会识别它(因为multiset中本身存储的就是<value, value>组成的键值对,因此value本身就是key,key就是value,类型为T). multiset元素的值不能在容器中进行修改(因为元素总是const的),但可以从容器中插入或删除。

3. 在内部,multiset中的元素总是按照其内部比较规则(类型比较)所指示的特定严格弱排序准则
进行排序。

4. multiset容器通过key访问单个元素的速度通常比unordered_multiset容器慢,但当使用迭代器遍历时会得到一个有序序列。

5. multiset底层结构为二叉搜索树(红黑树)。
 

2、multiset的使用

multiset中的接口可以参考set,功能都是类似的,这里就不具体演示了

但是需要注意下面七点:

1. multiset中再底层中存储的是<value, value>的键值对

2. mtltiset的插入接口中只需要插入即可

3. 与set的区别是,multiset中的元素可以重复,set是中value是唯一的

4. 使用迭代器对multiset中的元素进行遍历,可以得到有序的序列

5. multiset中的元素不能修改

6. 在multiset中找某个元素,时间复杂度为$O(log_2 N)$

7. multiset的作用:可以对元素进行排序

七、代码

#define _CRT_SECURE_NO_WARNINGS 1
#include <iostream>
#include <vector>
#include <string>
#include <map>
#include <set>
using namespace std;
void TestMap()
{map<string, string> m;m.insert(pair<string, string>("peach", "桃子"));//构造的时候直接利用pair进行插入m.insert(make_pair("banan", "香蕉"));//利用make_pair函数进行插入m["apple"] = "苹果";//插入+修改  最常用的cout << m.size() << endl;for (auto& e : m)cout << e.first << "--->" << e.second << endl;cout << endl;auto ret = m.insert(make_pair("peach", "桃色"));if (ret.second)cout << "<peach, 桃色>不在map中, 已经插入" << endl;elsecout << "键值为peach的元素已经存在:" << ret.first->first << "--->"<< ret.first->second << " 插入失败" << endl;m.erase("apple");if (1 == m.count("apple"))cout << "apple还在" << endl;elsecout << "apple被吃了" << endl;
}void TestSet()
{int arr[] = { 1, 3, 5, 7, 9, 2, 4, 6, 8, 0, 1, 3, 5, 7, 9, 2, 4, 6, 8, 0 };set<int> s;for (int i = 0; i < sizeof(arr) / sizeof(arr[0]); i++)s.insert(arr[i]);cout << s.size() << endl;for (auto& e : s)cout << e << " ";cout << endl;for (auto it = s.rbegin(); it != s.rend(); ++it)cout << *it << " ";cout << endl;cout << s.count(3) << endl;
}int main()
{//TestMap();TestSet();return 0;
}

八、思维导图

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/825353.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

PMM2 MySQL监控管理工具

目录 1. PMM介绍 2. 安装PMM服务端 2.1 安装docker 2.1.1 下载docker 2.1.2 上传docker包 2.1.3 启动守护进程 2.1.4 查看docker状态 2.2 安装PMM 2.2.1 下载镜像 2.2.2 load镜像 2.2.3 查看镜像 2.2.4 创建容器 2.2.5 运行镜像 2.2.6 验证PMM服务器 2.2.7 删除…

外包干了16天,技术倒退明显

先说情况&#xff0c;大专毕业&#xff0c;18年通过校招进入湖南某软件公司&#xff0c;干了接近6年的功能测试&#xff0c;今年年初&#xff0c;感觉自己不能够在这样下去了&#xff0c;长时间呆在一个舒适的环境会让一个人堕落&#xff01; 而我已经在一个企业干了四年的功能…

【剪映专业版】09定格、倒放、镜像、旋转、裁剪

视频课程&#xff1a;B站有知公开课【剪映电脑版教程】 分别为定格、倒放、镜像、旋转、裁剪 定格 时间指示器移动到需要定格的地方&#xff0c;点击定格&#xff0c;自动生成一张图片&#xff0c;时长为3秒。 定格出来的画面&#xff0c;可以任意调整长短时间。 如果需要导…

MySQL高级(性能分析-查看执行频次、慢查询日志)

目录 1、SQL性能分析 1.1、SQL执行频率 1.2、慢查询日志 1、SQL性能分析 1.1、SQL执行频率 MySQL 客户端连接成功后&#xff0c;通过 show [ session | global ] status 命令可以提供服务器状态信息。通过如下指令&#xff0c;可以查看当前数据库的 insert、update、delete、…

使用vite从头搭建一个vue3项目(四)使用axios封装request.js文件,并使用proxy解决跨域问题

目录 一、创建request.js文件二、创建axios实例三、创建请求、响应拦截器四、使用 request.js&#xff0c;测试接口&#xff1a;https://api.uomg.com/api/rand.qinghua1、调取接口代码书写2、注意&#xff08;跨域问题&#xff09; axios 的二次封装有三个要点&#xff1a; 创…

【智能算法】霸王龙优化算法(TROA)原理及实现

目录 1.背景2.算法原理2.1算法思想2.2算法过程 3.结果展示4.参考文献 1.背景 2023年&#xff0c;VSDM Sahu等人受到霸王龙狩猎行为启发&#xff0c;提出了霸王龙优化算法&#xff08;Tyrannosaurus Optimization Algorithm, TROA&#xff09;。 2.算法原理 2.1算法思想 TR…

【系统分析师】系统规划

文章目录 1、项目的机会选择2、可行性分析3、成本效益分析3.1 基本概念3.2 盈亏临界分析3.3 净现值分析3.4 投资回收期 截图&#xff1a;希赛讲义 视频&#xff1a;B站 系统规划对应的是 立项 阶段 1、项目的机会选择 2、可行性分析 3、成本效益分析 3.1 基本概念 例题 3.2 盈…

边缘计算智能分析网关V4地面垃圾AI检测算法介绍及场景应用

在传统的卫生监管场景中&#xff0c;无法及时发现地面遗留的垃圾&#xff0c;通过人工巡逻的方式需要大量的人力、物力和时间&#xff0c;而且效率不高&#xff0c;并存在一定的滞后性&#xff0c;而采用地面垃圾AI检测算法则可以大大提高监管效率。 TSINGSEE青犀AI智能分析网…

windows10安装Tensorflow-gpu 2.10.0

windows10安装Tensorflow-gpu 2.10.0 本文主要目的是 从0开始演示 在windows10 平台安装Tensorflow-gpu 2.10.0。 Tensorflow-gpu 2.10.0 之后的版本&#xff0c;不再支持这样的安装方式&#xff0c;如果有需要&#xff0c;请参考wsl安装ubuntu的方式&#xff0c;进行安装。 …

短视频矩阵源头====技术文档交付

短视频矩阵源头技术文档交付 搭建短视频矩阵系统源码需要以下步骤&#xff1a; 1. 确定系统需求和功能&#xff1a;明确系统需要支持哪些功能&#xff0c;例如短视频的上传、存储、播放、分享、评论、点赞等。 2. 选择合适的编程语言和框架&#xff1a;根据需求选择合适的编程…

存储人视角:人工智能AI + 大模型

原文来自于知乎存储专栏&#xff1a; 存储人视角&#xff1a;人工智能AI 大模型 前沿 我的角色 背景 AI 出场 效果 一个宠娃狂魔 娃喜爱并有奥特曼玩具 她的奥特曼玩具会跳舞了 娃对我的崇拜和爱又多了一分......amazing 杭州网商路艾弗森 球队需要制作LOGO 形象生动…

【办公软件word小技巧】如何一键提取word中的图片 几十张 几百张均可一键提取

在日常生活和工作中&#xff0c;我们经常会遇到需要从Word文档中提取图片的情况。无论是为了单独保存这些图片&#xff0c;还是为了在其他地方使用它们&#xff0c;一键提取Word中的图片都是一个非常实用的技能。提取Word文件中的图片并不是一件复杂的事情&#xff0c;只要掌握…

照片jpg格式小于50kb怎么弄?jpg压缩到指定大小

我们经常需要处理大量的图片&#xff0c;特别是在分享到社交媒体时&#xff0c;然而&#xff0c;图片文件的大小常常成为困扰我们的问题&#xff0c;尤其是当我们的设备存储空间有限时。有些平台甚至会需要将图片压缩到50kb大小&#xff0c;那么&#xff0c;如何有效地压缩图片…

WAF攻防-权限控制代码免杀异或运算变量覆盖混淆加密传参

知识点 1、脚本后门基础&原理 2、脚本后门查杀绕过机制 3、权限维持-覆盖&传参&加密&异或等 章节点&#xff1a; WAF绕过主要集中在信息收集&#xff0c;漏洞发现&#xff0c;漏洞利用&#xff0c;权限控制四个阶段。 代码表面层免杀-ASP&PHP&JSP&a…

电商数据接口开发|淘宝商品接口|天猫商品接口|京东商品接口|拼多多商品接口|API接口申请指南

电商数据接口开发涉及到多个电商平台&#xff0c;包括淘宝、天猫、京东和拼多多等。这些平台都提供了丰富的API接口&#xff0c;以便开发者能够获取商品信息、订单数据等&#xff0c;从而构建出各种电商应用和服务。 1.请求方式&#xff1a;HTTP POST GET &#xff08;复制薇&…

Python经典游戏:乒乓球对战(单人+双人模式)

Python108款&#xff0c;小游戏集合&#xff0c;总有一个是你想要的 中国象棋 像素鸟 五子棋 24点小游戏 贪吃蛇 扫雷 俄罗斯方块 魂斗罗 消消乐 坦克大战 外星人入侵 汤姆猫 斗地主 乒乓球 推箱子 植物大战僵尸 围棋 超级玛丽 飞机大战 迷宫 滑雪 吃豆人…等等 &#xff0…

基于springboot实现信息化在线教学平台设计【项目源码+论文说明】计算机毕业设计

基于springboot实现信息化在线教学平台设计演示 摘要 随着信息技术在管理上越来越深入而广泛的应用&#xff0c;管理信息系统的实施在技术上已逐步成熟。本文介绍了信息化在线教学平台的开发全过程。通过分析信息化在线教学平台管理的不足&#xff0c;创建了一个计算机管理信息…

【OpenGL开发】PyQt在关闭应用程序时没有运行析构函数的问题

PyQt在关闭应用程序时没有运行析构函数的问题 目录 一、说明二、python的析构函数三、通用版QT5 存在一些问题四、python版PyQt5 存在一些问题五、OpenGL的析构问题5.1 OpenGL很脆弱,这不是危言耸听5.2 以上OpenGL问题解决方法六、一些保留意见一、说明 应用QT做程序界面,在…

电视盒子哪个牌子好?博主总结网络电视盒子推荐

电视盒子是我们使用最多的产品&#xff0c;追剧、游戏、上网课都离不开电视盒子&#xff0c;但很多朋友不知道电视盒子哪个牌子好&#xff0c;我这周共计测评了18款不同品牌的电视盒子&#xff0c;今天整理了五款网络电视盒子推荐&#xff0c;想买电视盒子可以看看下面这些。 第…

vscode 配置go环境

https://www.zhihu.com/question/486786946/answer/2723663432 注意一定要安装最新版,否则不容易debug //main.go package main //说明hello.go这个文件在main这个包中import "fmt" //导入内置包&#xff0c;可以使用其中函数等func main() {fmt.Println("Hello…