【C++】学习笔记——哈希_1

文章目录

  • 十八、哈希
    • 1. unordered系列关联式容器
    • 2. 底层结构
      • 哈希函数
      • 哈希冲突
  • 未完待续


十八、哈希

1. unordered系列关联式容器

在C++11中,STL又提供了4个unordered系列的关联式容器,这四个容器与红黑树结构的关联式容器使用方式基本类似,只是其底层结构不同。
在这里插入图片描述
->查看文档戳这里<-
在这里插入图片描述
在这里插入图片描述

在这里插入图片描述
在这里插入图片描述
其实这4个加上 unordered 前缀的容器与不加这个前缀的容器几乎没什么不同,唯一不同的就是:unordered容器底层实现采用的是哈希表的存储结构,并不会对数据排序。
如下示例大家就能理解unordered容器了:

#include <iostream>
#include <unordered_map>
#include <unordered_set>
#include <map>
#include <set>
using namespace std;// 集合
void test_set1()
{set<int> s;s.insert(1);s.insert(7);s.insert(4);s.insert(9);s.insert(2);cout << "set : ";for (auto e : s) cout << e << " ";cout << endl;
}// 无序集合
void test_unordered_set1()
{unordered_set<int> s;s.insert(1);s.insert(7);s.insert(4);s.insert(9);s.insert(2);cout << "unordered_set : ";for (auto e : s) cout << e << " ";cout << endl;
}int main()
{test_set1();test_unordered_set1();return 0;
}

结果:
在这里插入图片描述
可以看到的是,unordered_set不仅没有排序,还把原数组给搞乱了。
哪unordered容器有什么优势呢?这不被普通的完爆? 其实unordered容器为了加快查找速度,存储数据的时候搞了点小把戏,使其尽可能的在常数时间内查找到某一元素 。因此,unordered容器比普通容器查找要快,但它通常在遍历元素子集的范围迭代方面效率较低。

2. 底层结构

哈希函数

顺序结构以及平衡树中,元素关键码与其存储位置之间没有对应的关系,因此在查找一个元素时,必须要经过关键码的多次比较。顺序查找时间复杂度为O(N),平衡树中为树的高度,即O( l o g 2 N log_2 N log2N),搜索的效率取决于搜索过程中元素的比较次数。但是有没有一种方式,可以让我们只需要一次即可直接找到元素呢?
答案是有的,我们只需要建立存储位置与数据之间的映射关系即可。这种存储方式叫做哈希方法。哈希方法中使用的转换函数称为哈希(散列)函数,构造出来的结构称为 哈希表(Hash Table) ,或者称散列表。
例如:数据集合{1,7,6,4,5,9};
哈希函数设置为:hash(key) = key % capacity;capacity为存储元素底层空间总的大小。
在这里插入图片描述
很多人都会想到,这样的存储方法是不安全的,很容易出现 不同关键字通过相同哈希哈数计算出相同的哈希地址,这种现象称为 哈希冲突(哈希碰撞)

哈希冲突

引起哈希冲突的一个原因可能是:哈希函数设计不够合理。
但是,再合理的哈希函数也不能对应所有情况,哈希冲突是无法避免的 。因此我们需要着手解决哈希冲突。比如上面那个例子,当再次插入 15 时,会因为 15 % 10 = 5 ,而下标5已经被占用,我们可以向后遍历,直到找到一个空位放下 ,这是闭散列方法。当然还有其他的方法,比如开散列。开散列法又叫链地址法(开链法),首先对关键码集合用散列函数计算散列地址,具有相同地址的关键码归于同一子集合,每一个子集合称为一个桶,各个桶中的元素通过一个单链表链接起来,各链表的头结点存储在哈希表中。
在这里插入图片描述


未完待续

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

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

相关文章

Linux云计算 |【第二阶段】AUTOMATION-DAY1

主要内容&#xff1a; 版本控制&#xff08;集中式、分布式&#xff09;、Git基础&#xff08;服务端、客户端部署&#xff0c;基础命令操作、文档版本管理&#xff09;、Git进阶&#xff08;数据恢复、分支、冲突管理&#xff09; 一、版本控制概念 版本控制是一种记录文件变…

iterm2工具的使用|MAC电脑终端实现分屏|iterm2开启滚动操作

iterm2 工具概括 iTerm2 是一款非常强大的终端工具。 iTerm2 最初是为 macOS 开发的,但也有 Windows 、Linux 发行版&#xff08;Ubuntu、centos…&#xff09;可用。 应用场景 Mac操作系统中想实现终端分屏 iterm2 工具特点 多标签和分屏: 可以在同一个窗口中打开多个标签…

leetcode日记(48)排列序列

这道题想到了规律就不算难&#xff0c;列了好几个示例想出的规律&#xff0c;试着排序几个就会了 class Solution { public:string getPermutation(int n, int k) {string result;int m1;int i1;for(i;i<n;i) m*i;i--;int pm/i;string s;for(int j0;j<n;j) s.append(to_…

基于VUE的软件项目开发管理系统/项目管理系统/软件开发过程管理系统的设计与实现

摘 要 在Internet高速发展的今天&#xff0c;我们生活的各个领域都涉及到计算机的应用&#xff0c;其中包括软件项目开发管理系统的网络应用&#xff0c;在外国软件项目开发管理系统已经是很普遍的方式&#xff0c;不过国内的软件项目开发管理可能还处于起步阶段。软件项目开发…

【计算机网络】三次握手、四次挥手

问&#xff1a;三次握手 四次挥手 TCP 连接过程是 3 次握手&#xff0c;终止过程是 4 次挥手 3次握手 第一步&#xff1a;客户端向服务器发送一个带有 SYN&#xff08;同步&#xff09;标志的包&#xff0c;指示客户端要建立连接。 第二步&#xff1a;服务器收到客户端的请求…

QtCreator和QtDesignStudio最佳实践

一、QTC和QDS工作流概述 很多初学者对 QDS(Qt Design Studio) 和 QTC(Qt Creator)如何配合经常存有疑问&#xff0c;本文介绍具体的工作流程。 工作流程 1.产品设计&#xff1a;通过PS、Figma、XD等专业工具设计页面视觉和原型。 2.QDS 原型制作&#xff1a;导入设计源文件、…

react中如何mock数据

1.需求说明 因为前后端分离开发项目&#xff0c;就会存在前端静态页面写好了&#xff0c;后端数据接口还没写好&#xff1b;这时候前端就需要自己定义数据来使用。 定义数据有三种方式&#xff1a;直接写死数据、使用mock软件、json-server工具 这里讲解通过json-server工具…

如何通过一条SQL变更多个分库分表?

数据库发展到今天&#xff0c;分库分表已经不是什么新鲜话题了&#xff0c;传统的单节点数据库架构在数据量和访问频次达到一定规模时&#xff0c;会出现性能瓶颈和扩展性问题&#xff0c;而分库分表技术通过将数据分散到多个数据库实例中来分担负载&#xff0c;从而提升系统的…

Electron的入门介绍与使用(1)共30节

Electron是一个使用 JavaScript、HTML 和 CSS 构建桌面应用程序的框架。 嵌入 Chromium 和 Node.js 到 二进制的 Electron 允许您保持一个 JavaScript 代码代码库并创建 在Windows上运行的跨平台应用 macOS和Linux——不需要本地开发 经验。 入门指南​ Electron 是网页应用 …

IEDA怎么把springboot项目 启动多个

利用Idea提供的Edit Configurations配置应用参数。 点击Modify Options进行添加应用参数&#xff1a; 确保这里勾选

宿舍生活新升级:智能指纹锁的便捷体验(嘉立创EDA设计)

宿舍生活新升级&#xff1a;智能指纹锁的便捷体验 引言 宿舍生活总是充满挑战和乐趣&#xff0c;但有时也会因为一些小事情而变得复杂。比如&#xff0c;忘记带钥匙或者需要频繁地给室友开门。随着科技的发展&#xff0c;智能设备逐渐走进我们的生活&#xff0c;为日常带来便…

每日好题(2)

#define _CRT_SECURE_NO_WARNINGS #include <stdio.h> int main(void) {int arr[6] { 1,2,3,4,5,6 };char* p arr;int sz sizeof(arr) / sizeof(arr[0]);for (int a 0; a < sz; a){printf("%d\n", *p);p 4;}return 0; }这串代码遍历打印数组的结果是没…

在 VM 虚拟机中安装 openEuler + 桌面

在 VM 虚拟机中安装 openEuler 1 介绍2 步骤语言Root 账户安装位置网络和主机名自动检索到【推荐】手动配置网络 软件选择安装完成登录测试网络curl ip / ping ipip link show / ip a如网络不通&#xff0c;可检查网卡状态和dns配置 安装命令设置以图形界面的方式启动【dde】第…

Python Django功能强大的扩展库之channels使用详解

概要 随着实时 web 应用程序的兴起,传统的同步 web 框架已经无法满足高并发和实时通信的需求。Django Channels 是 Django 的一个扩展,旨在将 Django 从一个同步 HTTP 框架转变为一个支持 WebSockets、HTTP2 和其他协议的异步框架。它不仅能够处理传统的 HTTP 请求,还可以处…

封装分页组件(Pagination)v2版本

使用须知&#xff1a;基于项目内已安装vue2eleme-ui&#xff0c; 则可以百分百直接套用&#xff0c;使用简介明了&#xff01;&#xff01; 一、封装component组件 component/Pagination/index.js <template><div :class"{ hidden: hidden }" class"…

动态规划之三—— 从暴力递归到动态规划_数字字符串转字母字符串

题目&#xff1a; 规定1 和A 对应&#xff0c;2 和B对应&#xff0c;3 和C 对应 ... 那么一个数字字符串&#xff0c;比如“111” 就可以转化为&#xff1a;“AAA” 、“KA”、“AK” 。要求&#xff1a;给定一个只有数字字符组成的字符串str&#xff0c; 返回有多少种转化结果…

客户端与服务器通讯详解(4):支持实时通讯的协议

在之前的章节中&#xff0c;贝格前端工场给大家分享了客户端与服务器通讯详解定义、流程、协议、方式。本次重点分享实时通讯方式是什么&#xff0c;该如何实现&#xff0c;有哪些协议&#xff0c;欢迎大家点赞评论转发。 一、客户端与服务器实时通讯是什么 客户端与服务器实…

SQL labs-SQL注入(二)

环境搭建参考 SQL注入&#xff08;一&#xff09; 一&#xff0c;SQL labs-less2。 http://192.168.61.206:8001/Less-2/?id-1 union select 1,2,group_concat(username , password) from users-- 与第一关没什么太大的不同&#xff0c;唯一区别就是闭合方式为数字型。 二…

解决:uniapp 小程序 使用swiper 内部嵌套另外一个拥有左右滑动组件导致滑动冲突

解决办法 在swiper-item 内增加这个属性进行包裹 touchmove.stop <div touchmove.stop><qiun-data-charts type"area" :opts"optsStg" :chartData"dateDataStg" /> </div>

微信小程序中Map组件Marker中把Label文字信息通过按钮显示或隐藏

wxml页面按钮 <button bindtap"toggleLabel">Toggle Label</button>js data:{labelMarkerId: null // 记录当前显示文本的标记的 id }, //按钮切换显示 toggleLabel() {// 判断当前是否有显示的文本标记if (this.data.labelMarkerId ! null) {// 如果…