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

【C++标准模版库】unordered_map和unordered_set的介绍及使用

unordered_map和unordered_set

  • 一.unordered_set
    • 1.unordered_set类的介绍
    • 2.unordered_set和set的使用差异
  • 二.unordered_map
    • 1.unordered_map和map的使用差异
  • 三.unordered_multimap/unordered_multiset
  • 四.unordered_map/unordered_set的哈希相关接口

一.unordered_set

1.unordered_set类的介绍

  1. unordered_set的声明如下,Key就是unordered_set底层关键字的类型。

在这里插入图片描述

  1. unordered_set默认要求Key支持转换为整形,如果不支持或者想按自己的需求走可以自行实现支持将Key转成整形的仿函数传给第⼆个模板参数。

  2. unordered_set默认要求Key支持比较相等,如果不支持或者想按自己的需求走可以自行实现支持将Key比较相等的仿函数传给第三个模板参数。

  3. unordered_set底层存储数据的内存是从空间配置器申请的,如果需要可以自己实现内存池,传给第四个参数。

  4. 一般情况下,我们都不需要传后三个模板参数。

  5. unordered_set底层是用哈希桶实现,增删查平均效率是O(1) 迭代器遍历不再有序,为了跟set
    区分,所以取名unordered_set。

  6. set和unordered_set的功能高度相似,只是底层结构不同,有一些性能和使用的差异,这里只讲他们的差异部分。

2.unordered_set和set的使用差异

unordered_set文档

  1. 查看文档我们会发现unordered_set的支持增删查且跟set的使用一模一样,关于使用我们这里就不再赘述和演示了。

  2. unordered_set和set的第一个差异是对key的要求不同,set要求Key支持小于比较,而unordered_set要求Key支持转成整形且支持等于比较,要理解unordered_set的这个两点要求得后续我们结合哈希表底层实现才能真正理解,也就是说这本质是哈希表的要求。

  3. unordered_set和set的第⼆个差异是迭代器的差异,set的iterator是双向迭代器unordered_set是单向迭代器,其次set底层是红黑树,红黑树是⼆叉搜索树,走中序遍历是有序的,所以set迭代器遍历是有序+去重。而unordered_set底层是哈希表,迭代器遍历是无序+去重

int main()
{//迭代器遍历有序+去重set<int> s = { 5,4,2,6,8,5,6,9,7,4,2,3,1 };set<int>::iterator sit = s.begin(); //双向迭代器while (sit != s.end()){cout << *sit << " "; //1 2 3 4 5 6 7 8 9++sit;}cout << endl;//迭代器遍历无序+去重unordered_set<int> us = { 5,4,2,6,8,5,6,9,7,4,2,3,1 };unordered_set<int>::iterator usit = us.begin(); //单向迭代器while (usit != us.end()){cout << *usit << " "; //5 4 2 6 8 9 7 3 1++usit;}cout << endl;return 0;
}
  1. unordered_set和set的第三个差异是性能的差异,整体而言大多数场景下,unordered_set的增删
    查改更快一些而更常用,因为红黑树增删查改效率是O(logN) ,而哈希表增删查平均效率是O(1) ,O(logN) 与O(1)差距不大。具体可以参看下面代码的演示的对比差异。
void test_set()
{const size_t N = 1000000;unordered_set<int> us;set<int> s;vector<int> v;v.reserve(N);srand(time(0));for (size_t i = 0; i < N; ++i){//v.push_back(rand()); //N比较大时,重复值比较多v.push_back(rand() + i); //重复值相对少//v.push_back(i); //没有重复,有序}size_t begin1 = clock();for (auto e : v){s.insert(e);}size_t end1 = clock();cout << "set insert:" << end1 - begin1 << endl;cout << "set插入数据个数:" << s.size() << endl << endl;size_t begin2 = clock();us.reserve(N);for (auto e : v){us.insert(e);}size_t end2 = clock();cout << "unordered_set insert:" << end2 - begin2 << endl;cout << "unordered_set插入数据个数:" << s.size() << endl << endl;int m1 = 0;size_t begin3 = clock();for (auto e : v){auto ret = s.find(e);if (ret != s.end()){++m1; //找到:次数+1}}size_t end3 = clock();cout << "set find:" << end3 - begin3 << " -> " << m1 << endl;int m2 = 0;size_t begin4 = clock();for (auto e : v){auto ret = us.find(e);if (ret != us.end()){++m2; //找到:次数+1}}size_t end4 = clock();cout << "unorered_set find:" << end4 - begin4 << " -> " << m2 << endl << endl;size_t begin5 = clock();for (auto e : v){s.erase(e);}size_t end5 = clock();cout << "set erase:" << end5 - begin5 << endl;size_t begin6 = clock();for (auto e : v){us.erase(e);}size_t end6 = clock();cout << "unordered_set erase:" << end6 - begin6 << endl << endl;
}int main()
{test_set();return 0;
}

在这里插入图片描述

二.unordered_map

1.unordered_map和map的使用差异

在这里插入图片描述

  1. 查看文档我们会发现unordered_map的支持增删查且跟map的使用一模一样,关于使用我们这里就不再赘述和演示了。

  2. unordered_map和map的第一个差异是对key的要求不同,map要求Key支持小于比较,而
    unordered_map要求Key支持转成整形且⽀持等于比较,要理解unordered_map的这个两点要求
    得后续我们结合哈希表底层实现才能真正理解,也就是说这本质是哈希表的要求。

  3. unordered_map和map的第⼆个差异是迭代器的差异,map的iterator是双向迭代器,
    unordered_map是单向迭代器,其次map底层是红黑树,红黑树是⼆叉搜索树,走中序遍历是有
    序的,所以map迭代器遍历是Key有序+去重。而unordered_map底层是哈希表,迭代器遍历是
    Key无序+去重。

  4. unordered_map和map的第三个差异是性能的差异,整体而言大多数场景下,unordered_map的
    增删查改更快一些,因为红黑树增删查改效率是O(logN) ,而哈希表增删查平均效率是O(1)。

三.unordered_multimap/unordered_multiset

  1. unordered_multimap/unordered_multiset跟multimap/multiset功能完全类似,支持Key冗余。
  2. unordered_multimap/unordered_multiset跟multimap/multiset的差异也是三个方面的差异,key的要求的差异,iterator及遍历顺序的差异,性能的差异。
  3. multi版本由于Key冗余,所以不支持operator []
int main()
{unordered_map<string, string> dict1;dict1.insert({ "left", "向左" });dict1.insert({ "left", "离开" }); //插入失败dict1.insert({ "left", "留下" }); //插入失败unordered_multimap<string, string>::iterator it1 = dict1.begin();while (it1 != dict1.end()){cout << it1->first << ":" << it1->second << endl;++it1;}cout << endl;unordered_multimap<string, string> dict2;dict2.insert({ "left", "向左" });dict2.insert({ "left", "离开" }); //插入成功dict2.insert({ "left", "留下" }); //插入成功unordered_multimap<string, string>::iterator it2 = dict2.begin();while (it2 != dict2.end()){cout << it2->first << ":" << it2->second << endl;++it2;}cout << endl;return 0;
}

在这里插入图片描述

四.unordered_map/unordered_set的哈希相关接口

在这里插入图片描述

Buckets和Hash policy系列的接口分别是跟哈希桶和负载因子相关的接口,日常使用的角度我们不需
要太关注,需要结合哈希表底层,才能明白。

相关文章:

【C++标准模版库】unordered_map和unordered_set的介绍及使用

unordered_map和unordered_set 一.unordered_set1.unordered_set类的介绍2.unordered_set和set的使用差异 二.unordered_map1.unordered_map和map的使用差异 三.unordered_multimap/unordered_multiset四.unordered_map/unordered_set的哈希相关接口 一.unordered_set 1.unord…...

深度解析Transformer:从自注意力到MLP的工作机制

深度解析Transformer&#xff1a;从自注意力到MLP的工作机制 以下大部分内容本来自对3Blue1Brown的视频讲解的整理组织 一、Transformer的目标 为了简化问题&#xff0c;这里讨论的模型目标是接受一段文本&#xff0c;预测下一个词。这种任务对模型提出了两大要求&#xff1a;…...

《米小圈动画成语》|在趣味中学习,在快乐中掌握成语知识!

作为一名家长&#xff0c;我一直希望孩子能够在学习的过程中既感受到乐趣&#xff0c;又能获得真正的知识。成语作为中华文化的精华&#xff0c;虽然意义深远、简洁凝练&#xff0c;但对于一个小学生来说&#xff0c;学习和理解这些言简意赅的成语无疑是一个挑战。尤其是有些成…...

linux系统之jar启动脚本

编辑linux启动脚本 执行 vi run_blog 按i 进入编辑&#xff0c;复制以下代码&#xff0c;并根据当前环境修改三个参数。以下是详细完整脚本代码&#xff1a; #!/bin/bash# 配置部分 JAR_PATH"/path/to/your/app.jar" # 替换为你的 JAR 文件的实际路径 L…...

简单认识Maven 2-Maven坐标

Maven坐标 在 Maven 中&#xff0c;坐标&#xff08;Coordinates&#xff09;用于唯一标识一个项目或依赖项&#xff0c;就像在现实世界中通过经纬度来确定一个地理位置一样。Maven 坐标由三个主要部分组成&#xff1a;groupId、artifactId 和 version。 groupId&#xff08;…...

Xilinx UltraScale系列FPGA纯verilog图像缩放,工程项目解决方案,提供2套工程源码和技术支持

目录 1、前言工程概述免责声明FPGA高端图像处理培训 2、相关方案推荐我这里已有的FPGA图像缩放方案本方案在Xilinx Artix7 系列FPGA上的应用本方案在Xilinx Kintex7 系列FPGA上的应用本方案在Xilinx Zynq7000 系列FPGA上的应用本方案在国产FPGA紫光同创系列上的应用本方案在国产…...

React(二) JSX中的this绑定问题;事件对象参数传递;条件渲染;列表渲染;JSX本质;购物车案例

文章目录 一、jsx事件绑定1. 回顾this的绑定方式2. jsx中的this绑定问题(1) 方式一&#xff1a;bind绑定(2) 方式二&#xff1a;使用 ES6 class fields 语法(3) 方式三&#xff1a;直接传入一个箭头函数(重要) 3.事件参数传递(1) 传递事件对象event(2) 传递其他参数 4. 事件绑定…...

前端开发攻略---取消已经发出但是还未响应的网络请求

目录 注意&#xff1a; 1、Axios实现 2、Fetch实现 3、XHR实现 注意&#xff1a; 当请求被取消时&#xff0c;只会本地停止处理此次请求&#xff0c;服务器仍然可能已经接收到了并处理了该请求。开发时应当及时和后端进行友好沟通。 1、Axios实现 <!DOCTYPE html> &…...

韩信走马分油c++

韩信走马分油c 题目算法代码 题目 把油桶里还剩下的10斤油平分&#xff0c;只有一个能装3斤的油葫芦和一个能装7斤的瓦罐。如何分。 算法 油壶编号0&#xff0c;1&#xff0c;2。不同倒法有&#xff1a;把油从0倒进0&#xff08;本壶到本壶&#xff0c;无效&#xff09;&…...

【Linux】Anaconda下载安装配置Pytorch安装配置(保姆级)

目录 Anaconda下载 Anaconda安装 conda init conda --v Conda 配置 conda 环境创建 conda info --envs conda list Pytorch安装配置 检验安装情况 检验是否可以使用GPU Anaconda下载 可以通过两种途径完成Anaconda安装包的下载 途径一&#xff1a;本地windows下…...

渗透测试导论

渗透测试的定义和目的 渗透测试&#xff08;Penetration Testing&#xff09;是一项安全演习&#xff0c;网络安全专家尝试查找和利用计算机系统中的漏洞。 模拟攻击的目的是识别攻击者可以利用的系统防御中的薄弱环节。 这就像银行雇用别人假装盗匪&#xff0c;让他们试图闯…...

鸿蒙学习笔记--搭建开发环境及Hello World

文章目录 一、概述二、开发工具下载安装2.1 下载开发工具DevEco Studio NEXT2.2 安装DevEco Studio 三、启动软件四、第一个应用Hello World4.1 创建应用4.2 创建模拟器4.3 开启Hyper-v功能4.4 启动虚拟机 剑子仙迹 诗号&#xff1a;何须剑道争锋&#xff1f;千人指&#xff0c…...

【ArcGIS风暴】ArcGIS字段计算器公式汇总

在GIS数据处理中,ArcGIS的字段计算器是一个强大的工具,它可以帮助我们进行各种数值计算、文本处理和逻辑判断。本文将为您整合和分类介绍ArcGIS字段计算器中的常用公式,并通过实例说明它们的应用。 文章目录 一、数值计算类二、文本处理类三、日期和时间类四、逻辑判断类五、…...

探索秘境:如何使用智能体插件打造专属的小众旅游助手『小众旅游探险家』

文章目录 摘要引言智能体介绍和亮点展示介绍亮点展示 已发布智能体运行效果智能体创意想法创意想法创意实现路径拆解 如何制作智能体可能会遇到的几个问题快速调优指南总结未来展望 摘要 本文将详细介绍如何使用智能体平台开发一款名为“小众旅游探险家”的旅游智能体。通过这…...

机械臂力控方法概述(一)

目录 1. MoveIt 适用范围 2. 力控制框架与 MoveIt 的区别 3. 力控方法 3.1 直接力控制 (Direct Force Control) 3.2 间接力控制 (Indirect Force Control) 3.2.1 柔顺控制 (Compliant Control) 3.2.2 阻抗控制 (Impedance Control) 3.2.3 导纳控制 (Admittance Control…...

1971. 寻找图中是否存在路径

有一个具有 n 个顶点的 双向 图&#xff0c;其中每个顶点标记从 0 到 n - 1&#xff08;包含 0 和 n - 1&#xff09;。图中的边用一个二维整数数组 edges 表示&#xff0c;其中 edges[i] [ui, vi] 表示顶点 ui 和顶点 vi 之间的双向边。 每个顶点对由 最多一条 边连接&#x…...

FLINK SQL语法(1)

DDL Flink SQL DDL&#xff08;Data Definition Language&#xff09;是Flink SQL中用于定义和管理数据结构和数据库对象的语法。以下是对Flink SQL DDL的详细解析&#xff1a; 一、创建数据库&#xff08;CREATE DATABASE&#xff09; 语法&#xff1a;CREATE DATABASE [IF…...

【Fargo】1:基于libuv的udp收发程序

开发UDP处理程序 我正在开发一个基于libuv的UDP发送/接收程序,区分发送端和接收端,设计自定义包数据结构,识别和处理丢包和乱序。 创建项目需求 用户正在要求一个使用libuv的C++程序,涉及UDP发送和接收,数据包包括序列号和时间戳,接收端需要检测丢包和乱序包。 撰写代…...

WebSocket介绍和入门案例

目录 一、WebSocket 详解1. 定义与特点&#xff1a;2. 工作原理&#xff1a;3. 应用场景&#xff1a; 二、入门案例 一、WebSocket 详解 1. 定义与特点&#xff1a; WebSocket 是一种在单个 TCP 连接上进行全双工通信的协议。它允许客户端和服务器之间进行实时、双向的数据传…...

k8s集群版本升级

Kubernetes 集群版本升级是为了获得最新的功能、增强的安全性和性能改进。然而&#xff0c;升级过程需要谨慎进行&#xff0c;特别是在生产环境中。通常&#xff0c;Kubernetes 集群的版本升级应遵循逐步升级的策略&#xff0c;不建议直接跳过多个版本。 Kubernetes 版本升级的…...

XML 和 SimpleXML 简介

XML 和 SimpleXML 简介 XML&#xff08;可扩展标记语言&#xff09;是一种用于存储和传输数据的标记语言。它定义了一组规则&#xff0c;用于在文档中编码数据&#xff0c;以便人和机器都能理解。XML 的设计目标是既易于人类阅读&#xff0c;也易于机器解析。SimpleXML 是 PHP…...

MySQL 中 LIKE 语句的 `%` 和 `_` 以及 BLOB 和 TEXT 的详细解析和案例示范

1. LIKE 语句中的 % 和 _ 用法 1.1 % 通配符的用法 % 通配符代表零个或多个字符。它是 MySQL 中用于模糊匹配的强大工具之一&#xff0c;可以在任何字符的位置使用。 示例 1&#xff1a;查找以特定字符开头的记录 假设我们有一个电商订单系统的 orders 表&#xff0c;其中包…...

git clone卡在Receiving objects

git clone卡在Receiving objects 一直卡主 $ git clone gitxxx.git Cloning into xxx... remote: Enumerating objects: 75926, done. remote: Counting objects: 100% (18844/18844), done. remote: Compressing objects: 100% (6566/6566), done. Receiving objects: 60% (…...

vue+ant 弹窗可以拖动

通过自定义指令实现拖拽功能 在main.js里加入drag自定义指令 我自己测试时发现modal不管如何设置宽度&#xff0c;居中等&#xff0c;他的初始的left都为0&#xff0c;如果不设置好&#xff0c;容易出现点击后刚开始移动弹窗会偏移一段距离。 Vue.directive(drag, {bind(el)…...

(42)MATLAB中使用fftshift绘制以零为中心的功率谱

文章目录 前言一、MATLAB代码二、仿真结果画图 前言 在分析信号的频率分量时&#xff0c;将零频分量平移到频谱中心会很有帮助。本例给出绘制以零为中心的功率谱的方法。 一、MATLAB代码 代码如下&#xff1a; f 1; % 余弦波的振荡频率&#xf…...

Windows本地部署中文羊驼模型(Chinese-Alpaca-Pro-7B)(通俗易懂版)

最近由于项目原因需要部署大语言模型, 但碍于经济实力, 只能部署在笔记本电脑上部署量化模型, &#xff08;电脑至少有16G运行内存&#xff09;&#xff0c;搜集了网上的相关部署资料仍然踩了不少坑&#xff0c;原因在于开源项目在不断更新&#xff0c;导致我们看了别人的教程仍…...

Web3的挑战与机遇:技术发展的现状分析

在Web3的世界中&#xff0c;去中心化和用户主权的理念正逐渐走向主流&#xff0c;推动了现有商业模式和技术生态系统的深刻变革。区块链技术及其核心应用之一——智能合约&#xff0c;正在促使这一转变的发生。智能合约的主要功能是通过自动化和预设协议执行&#xff0c;以减少…...

LangGraph - Hierarchical Agent Teams

本文翻译整理自 Hierarchical Agent Teams https://langchain-ai.github.io/langgraph/tutorials/multi_agent/hierarchical_agent_teams/ 文章目录 一、前言二、设置三、创建工具四、Helper Utilities五、定义代理 Team研究 Team文档写作Team 六、添加图层 一、前言 在前面的…...

2021-04-14 proteus中仿真时74HC245三态双向端口扩展输出

缘由proteus中仿真时74HC245输出时电平显示灰色&#xff08;不确定电平状态&#xff09;是为什么&#xff1f;-编程语言-CSDN问答 缘由C语言翻译单片机开关检测器-编程语言-CSDN问答 参考74ls245的工作原理及作用详解 - 电子发烧友网 参考74ls245_百度百科...

解决UNSPSC商品分类的层级不足的方法

《联合国标准产品和服务守则》&#xff08;UNSPSC&#xff09;是一个分层框架&#xff0c;旨在对产品和服务进行分类。其主要目标是通过提供统一的方法来对产品和服务进行分类&#xff0c;从而简化采购和供应链管理。 虽然 UNSPSC 有效地将产品分为各种商品类别&#xff0c;但…...