开散列哈希桶

通过上面这幅图,读者应该能较为直观地理解何为开散列,以及闭散列与开散列的区别在哪里 —— 数据的存储形式不同,至于其他的,如确定每个元素的哈希地址等一概相同。

与闭散列相比,开散列能够更好地处理发生冲突的元素 —— 假使我们要在上述闭散列中再插入 5 ,会因为 24 的先插入而导致 5 必须往后寻找空位置,进而影响 6 的插入等。

1. 什么是桶?

通过 HashFunc 计算每个元素的哈希地址,哈希地址相同的元素所组成的子集称为 哈希桶 ,这些元素通过单链表链接在一起。

如:4 % 10 == 24 % 10 == 34 % 10 == 44 % 10 == 4

开散列的每个桶中存的都是发生哈希冲突的元素。

2. 开散列框架搭建
  • HashFunc
template<class K>
struct HashFunc
{size_t operator()(const K& key){size_t ret = key;return ret;}
};// 为 string 写一个特化版本
template<>
struct HashFunc<string>
{size_t operator()(const string& s){size_t hash = 0;for (auto& e : s){hash = hash * 131 + e; // 131 是前辈用大量数据测试得到的值,可以尽大程度避免哈希冲突}return hash;}
};
  • HashNode
	template<class K, class V>struct HashNode{HashNode* _next;pair<K, V> _kv;HashNode(const pair<K, V>& kv):_next(nullptr),_kv(kv){}};
  • HashTable
	template<class K, class V, class Hash = HashFunc<K>>class HashTable{typedef HashNode<K, V> Node;public:HashTable(){_tables.resize(10);}private:vector<Node*> _tables;size_t _n = 0;};
3. Insert()
	bool Insert(const pair<K, V>& kv){if (Find(kv.first)) // 未实现的 Find,已存在则返回该元素哈希位置的指针,不存在则返回空return false;Hash hs;// 扩容 if (_n == _tables.size()) // STL 库中,开散列的负载因子设为 1{// ...}// 插入size_t hashi = hs(kv.first) % _tables.size();Node* newNode = new Node(kv);newNode->_next = _tables[hashi];_tables[hashi] = newNode;// 头插++_n;return true;}

再来聊一聊扩容逻辑。

与闭散列不同,我们不准备复用 Insert() 完成数据的拷贝 —— 假设哈希桶中已经存在 1000, 000 个元素,需要重新拷贝 1000, 000 个元素,再将原表中的元素一一释放。

更好的办法是,直接将原表中的节点 挂到 新表对应的哈希位置上

	// 扩容部分if (_n == _tables.size()){vector<Node*> newTable(2 * _tables.size(), nullptr);for (size_t i = 0; i < _tables.size(); i++){Node* cur = _tables[i];while (cur){Node* next = cur->_next;size_t hashi = hs(cur->_kv.first) % newTable.size();cur->_next = newTable[hashi];newTable[hashi] = cur;cur = next;}_tables[i] = nullptr;// 将原表置空}_tables.swap(newTable);// 不需要手动将 newTable delete[],编译器会自动调用 vector 的析构函数,// 且 swap 后,newTable 里全为空,不需要担心内存泄露的问题}
4. Find()Erase()
  • Find()
	Node* Find(const K& key){Hash hs;size_t hashi = hs(key) % _tables.size();Node* cur = _tables[hashi];while (cur){if (cur->_kv.first == key){break;}cur = cur->_next;}if (cur && cur->_kv.first == key)return cur;else return nullptr;}
  • Erase()

开散列的 Erase() 不能像闭散列那样,Find() 后直接删除。

调用 Find() 能得到 key 对应的 HashData 的指针,但无法得到前一个节点的指针,会造成一系列问题。

	bool Erase(const K& key){Hash hs;size_t hashi = hs(key) % _tables.size();Node* cur = _tables[hashi];Node* prev = nullptr; // prev 为前一个节点指针while (cur){if (cur->_kv.fisrt == key) // 找到了{if (prev) // prev 不为空,说明 cur 为中间节点{prev->_next = cur->_next;}else // prev 为空,说明 cur 为 _tables[hashi]{_tables[hashi] = cur->_next;}delete cur;--_n;return true;}prev = cur;cur = cur->_next;}return false;}

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

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

相关文章

Transformers 加速的一些常用技巧

Transformers 是一个强大的架构&#xff0c;但模型因其采用的自注意力机制&#xff0c;虽然能够有效地处理序列数据并捕获长距离依赖关系&#xff0c;但同时也容易导致在训练过程中出现OOM&#xff08;Out of Memory&#xff0c;内存不足&#xff09;或者达到GPU的运行时限制。…

AI大模型探索之路-训练篇22: ChatGLM3微调实战-从原理到应用的LoRA技术全解

系列篇章&#x1f4a5; AI大模型探索之路-训练篇1&#xff1a;大语言模型微调基础认知 AI大模型探索之路-训练篇2&#xff1a;大语言模型预训练基础认知 AI大模型探索之路-训练篇3&#xff1a;大语言模型全景解读 AI大模型探索之路-训练篇4&#xff1a;大语言模型训练数据集概…

MPLAB X IDE编译attiny1616工程报错却无报错信息

MPLAB X IDE(XC-8编译器)编译报错&#xff0c;无具体错误内容&#xff0c;仅显示需要xc-8 pro的警告。 内存占用率显示为81%&#xff0c;未超标。 原因&#xff1a;软件使用了microchip的bootloader功能。应用程序起始地址&#xff08;也是bootloader结束地址&#xff09;设置错…

社交巨头:探索Facebook的震撼力量

Facebook作为社交媒体领域的巨头&#xff0c;不仅在数字化社会中占据着重要地位&#xff0c;更是影响了人们的生活、工作和社交方式。本文将深入探索Facebook的震撼力量&#xff0c;从多个角度解读其在当今社会中的重要性和影响。 1. 全球用户覆盖的壮观规模 Facebook作为全球…

docker安装时报错:Error: Nothing to do

安装docker时报以下错误 解决方法&#xff1a; 1.下载关于docker的相关依赖环境 yum -y install yum-utils device-mapper-persistent-data lvm22.设置下载Docker的镜像源 yum-config-manager --add-repo http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo3…

FMEA存在的五个主要不足及改进措施——FMEA软件

免费试用FMEA软件-免费版-SunFMEA 在制造业和产品设计领域&#xff0c;失效模式与影响分析&#xff08;Failure Modes and Effects Analysis&#xff0c;简称FMEA&#xff09;被广泛运用&#xff0c;用于预防潜在的设计或制造缺陷。然而&#xff0c;尽管FMEA在风险管理方面发挥…

开发者集结号:大湾区 Open Source Day 邀您共探技术前沿

开源技术正以其开放、协作的特性&#xff0c;引领着软件开发的新潮流&#xff0c;是推动社会进步的重要力量。作为开发者&#xff0c;您是否渴望深入了解开源项目的前沿动态&#xff1f;由ALC深圳与2024中国互联网发展创新与投资大赛联合举办、FISCO金链盟深度参与的大湾区 Ope…

MySQL————创建存储过程函数

存储过程使用大纲 有参数传递 delimiter $$ 声明一个名称为get_student_introduce create procedure add_student_infor( in p_userName VARCHAR(20),in p_phone VARCHAR(11),in p_sex char(2),in p_introduce VARCHAR(255)) 开始操作 BEGIN 撰写真正在操作DMLDQL都行 INSE…

CSS---复合选择器、元素显示模式和背景(三)

一、CSS的复合选择器 1.1 什么是复合选择器 在CSS中&#xff0c;可以根据选择器的类型把选择器分为基础选择器和复合选择器&#xff0c;复合选择器是建立在基础选择器之上&#xff0c;对基本选择器进行组合形成的。 复合选择器是由两个或多个基础选择器连写组成&#xff0c;它…

【云原生】kubernetes核心组件

引言&#xff1a; Kubernetes 是为运行分布式集群而建立的&#xff0c;分布式系统的本质使得网络成为 Kubernetes 的核心和必要组成部分&#xff0c;了解 Kubernetes 网络模型可以使你能够正确运行、监控和排查应用程序故障。 一、Kubernetes的核心组件 1.1、Master组件 1.1.…

基于Springboot+Vue的Java项目-农产品直卖平台系统开发实战(附演示视频+源码+LW)

大家好&#xff01;我是程序员一帆&#xff0c;感谢您阅读本文&#xff0c;欢迎一键三连哦。 &#x1f49e;当前专栏&#xff1a;Java毕业设计 精彩专栏推荐&#x1f447;&#x1f3fb;&#x1f447;&#x1f3fb;&#x1f447;&#x1f3fb; &#x1f380; Python毕业设计 &am…

可道云teamOS企业网盘实用插件介绍:实时在线流程图编辑与分享,用在线流程图打造数字化工作流程

在使用企业网盘用于日常办公的情况下&#xff0c;有一些实用的在线小工具能为团队效率和协作带来一定的提升。 今天要给大家介绍的可道云teamOS的在线画流程图&#xff0c;是很值得介绍的一个在线工具。 在线流程图&#xff1a;直观展示&#xff0c;高效便捷 以往我们想要梳理…

FANUC机器人单轴零点标定时提示无法执行零点标定,由于重力补偿已启用,所有机器人轴的脉冲计数必须有效

FANUC机器人单轴零点标定时提示无法执行零点标定,由于重力补偿已启用,所有机器人轴的脉冲计数必须有效 首先,机器人由于长时间断电未使用,6个轴的编码器数据全部丢失,上电后报警SRVO-062, 有关SRVO-062故障报警的相关内容可参考以下链接: FANUC机器人SRVO-062报警原因分…

Scratch四级:第08讲 排序算法

第08讲 排序算法 教练&#xff1a;老马的程序人生 微信&#xff1a;ProgrammingAssistant 博客&#xff1a;https://lsgogroup.blog.csdn.net/ 讲课目录 常考的排序算法项目制作&#xff1a;“三个数排序”项目制作&#xff1a;“成绩查询”项目制作&#xff1a;“排序”项目制…

单片机智能灯控制系统源程序仿真原理图与论文全套资料

目录 1、设计描述 2、仿真图 3、程序 4、资料内容 资料下载地址&#xff1a;单片机智能灯控制系统源程序仿真原理图与论文全套资料下载 1、设计描述 设计了一款智能控制系统。 AT89C51LCD1602DS1302按键LED组成了这样一个完整的设计。 P2.0-P2.3 4个LED等代表庭院内的4…

架构设计之学新而知故

缘由 因为一些特殊的机缘&#xff0c;接触到洋葱架构等一些新架构设计概念。 尝试理解了一段时间&#xff0c;就想简单梳理下对它们的理解&#xff0c;以达到学新而知故 &#x1f603; 信息增益 以前计算机专业并不设置通信领域的信息论的专业课程&#xff0c;但是&#xf…

英语复习之英语形近词总结(四)

英语形近词总结复习第四部分&#xff1a; 单词 释义例句 genuine 英 /ˈdʒenjuɪn/ 美 /ˈdʒenjuɪn/ adj.真实的&#xff0c;真正的&#xff1b;诚恳的 1.Only genuine refugees can apply for asylum. 只有真正的难民才能申请政治避难。 《牛津词典》 2.This isnt a genui…

C++笔试强训day19

目录 1.小易的升级之路 2.礼物的最大价值 3.对称之美 1.小易的升级之路 链接 模拟就行&#xff0c;唯一可能是难点得就是gcd&#xff08;最大公约数&#xff09; #include <iostream> using namespace std; #define int long long const int N 1e5 10; int arr[N];…

利用IP地址查询解决被“薅羊毛”的方法

在互联网时代&#xff0c;随着各种网络诈骗手段的不断更新和演变&#xff0c;“薅羊毛”成为了一种常见的网络犯罪行为。其中&#xff0c;利用查询IP地址进行欺诈活动已经成为一种普遍的手段。当个人或组织的IP地址被不法分子查询后&#xff0c;可能会面临虚假注册、盗取个人信…

AVL Cruise与Simulink联合仿真(通过MATLAB DLL方式)

最近毕业设计需要用到AVL Cruise与Simulink进行联合仿真&#xff0c;分析汽车模型的经济性。下面介绍一下我所知的AVL Cruise与Simulink联合仿真的几种方式&#xff0c;它们各自的优缺点&#xff0c;以及DLL方式联合仿真的具体配置过程。我这里用的MATLAB软件版本是2021a&#…