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

【C++】unordered系列

前言:

在C++11及以后的标准中,unordered容器是标准模板库(STL)的一部分,提供了高效的数据结构选项,适用于需要快速查找和插入操作的场景。

unordered通常与关联容器一起使用,特别是unordered_mapunordered_set。这些容器提供了基于哈希表的实现,它们提供了与map和set相似的接口,但在查找、插入和删除操作上通常具有更高的性能,尤其是在处理大量数据时。

  • unordered_map是一个关联容器,它存储键值对,并根据键的哈希值进行排序,以实现快速的查找操作。
  • unordered_set则存储唯一的元素,并使用哈希表来管理这些元素,以便快速检查一个元素是否存在于集合中。

unordered_map的接口说明

注: unordered_mapunordered_set接口相似就只介绍一个接口。

unordered_map的接口说明

函数声明功能介绍
unordered_map构造不同格式的unordered_map对象

unordered_map的容量

函数声明功能介绍
bool empty()const检测unordered_map是否为空
size_t size() const获取unordered_map的有效元素个数

unordered_map的迭代器

函数声明功能介绍
begin返回unordered_map第一个元素的迭代器
end返回unordered_map最后一个元素下一个位置的迭代器
cbegin返回unordered_map第一个元素的const迭代器
cend返回unordered_map最后一个元素下一个位置的const迭代器

unordered_map的元素访问

函数声明功能介绍
operator[]返回与key对应的value,没有一个默认值

unordered_map的查询

函数声明功能介绍
iterator find(const K& key)返回key在哈希桶中的位置
size_t count(const K& key)返回哈希桶中关键码为key的键值对的个数

unordered_map的修改操作

函数声明功能介绍
insert向容器中插入键值对
erase删除容器中的键值对
void clear()清空容器中有效元素个数
void swap(unordered_map&)交换两个容器中的元素

unordered_map的桶操作

函数声明功能介绍
size_t bucket_count()const返回哈希桶中桶的总个数
size_t bucket_size(size_t n)const返回n号桶中有效元素的总个数
size_t bucket(const K& key)返回元素key所在的桶号

哈希

  1. **哈希(Hash)**是一种将任意大小的数据映射为固定大小值的函数,通常用于数据的快速查找和存储。
  2. **哈希表(Hash Table)**是基于哈希函数的一种数据结构,它通过计算关键字的哈希值来直接访问存储位置,从而实现常数时间复杂度的查找性能。

在这里插入图片描述

  • 在这里面的经过一系列的处理,得到的结果就映射到对应的位置,方便查找,加快了查找的速度。但是也会引发一系列的问题(哈希冲突)。

哈希函数

向上面的通过一系列的计算的过程就是哈希函数,有点类似于数学上的函数,一个数经过对应关系会得到两者的映射的关系。

常见的哈希函数

  1. 直接定址法:这种方法通过一个简单的线性函数计算哈希地址,公式为 Hash(Key) = A * Key + B。这种方法简单且分布均匀,但需要提前知道键值的分布情况。
  2. 除留余数法:这是一种常用的哈希函数,通过取关键字除以一个质数后的余数作为哈希地址,公式为 Hash(Key) = Key % p,其中 p 是一个不大于哈希表大小且最接近或等于哈希表大小的质数。
  3. 乘法取余法:这种方法通过将关键字乘以一个固定的数(通常是一个接近2的数),然后取结果的整数部分并进行取模运算来计算哈希地址。这种方法适用于处理字符串等非整数类型的键值。
  4. 平方取中法:这种方法适用于不清楚键值分布的情况,通过计算关键字平方后的中间几位数作为哈希地址。
  5. 折叠法:折叠法将键值分割成几部分,然后将这些部分叠加求和,并取后几位作为散列地址,适用于键值位数较多的情况。
  6. 标准库中的std::hash:C++标准库提供了std::hash模板,它为内置数据类型和一些标准库类型提供了默认的哈希函数实现。对于自定义类型,可以通过特化std::hash模板来提供自定义的哈希函数。

哈希冲突

哈希冲突是指不同的输入值通过哈希函数计算得到了相同的哈希值的现象。

  1. 在哈希表等数据结构中,哈希冲突是不可避免的,因为哈希函数的输出范围通常远小于可能的输入值范围。

解决方法

  • **开放定址法(闭散列):**当发生冲突时,会在哈希表中寻找下一个空位置来存放新元素。常见的开放定址法有线性探测和二次探测。线性探测是从冲突位置开始,依次向后查找空位置;二次探测则是通过更复杂的数学公式来确定下一个探测位置。
  • **再哈希法:**使用一个或多个备用哈希函数来处理冲突,将冲突的元素重新映射到哈希表的其他位置。
  • 链地址法(开散列):在哈希表的每个存储位置不是存储元素本身,而是存储一个指向元素的指针,冲突的元素会被添加到一个链表中。这种方法可以很好地处理大量冲突,但可能会导致链表过长,影响性能。
  • **建立公共溢出区:**为所有可能的哈希冲突预留一个或多个区域,冲突的元素被存储在这些区域中。

**注:**降低哈希冲突是提高效率的一个很好的方法

简单哈希

  • 在数组里面存储结构体
  • 定义哈希要有存在的状态定义了枚举
template<class K,class V>
struct Hashdata
{pair<K, V> _kv;state _state = EMPTY;
};
enum state
{EXIST,EMPTY,DELETE
};

Hash结构

  1. 两个模板参数K V结构
  2. 最后是存储hash的取值,针对整形、浮点型、字符串。进行仿函数的重写
template<class K,class V,class HashFunc = Defaulthashfunc<K>>
class Hash
{
public:private:vector<Hashdata<K, V>> _table;size_t _n = 0;
};

仿函数

  1. 在函数的内容的不确定的时候进行返回。
  2. 针对string字符串的直接进行特模板化。
  3. 针对26字母有不同的组合,要进行字符串的哈希化处理,目的是针对哈希冲突 (本次采用 BKDR算法)参考:字符串哈希算法
template<class K>
struct Defaulthashfunc
{size_t operator()(const K& key){return (size_t)key;}
};template<>
struct Defaulthashfunc<string>
{size_t operator()(const string& str){size_t hash = 0;for (auto e : str){hash *= 131;hash += e;}return hash;}
};

插入

  • 将hash表直接扩容,进行哈希计算
  • 进行哈希扩容 : 不建议直接将哈希表填写满,不利于哈数的查找,将哈希的负载因子(已经存储的数据比总空间的大小)设置到0.7到0.8之间即可。
  • 扩容: 重新定义哈希表(扩容后),进行数据的重新插入,进行交换
  • 进行哈希的冲突的解决
	bool insert(const pair<K, V>& kv){size_t hashi = 0;HashFunc hf;hashi = hf(kv.first) % _table.size();if ((_n * 10 / _table.size()) >= 7){size_t newsize = _table.size() * 2;Hash<K, V, HashFunc> newhash;newhash._table.resize(newsize);for (int i = 0; i < _table.size(); i++){if (_table[i]._state == EXIST){newhash.insert(_table[i]._kv);}}_table.swap(newhash._table);}//线性探测while (_table[hashi]._state == EXIST){++hashi;hashi %= _table.size();}_table[hashi]._kv = kv;_table[hashi]._state = EXIST;++_n;return true;}

开放定址法(闭散列)

发生冲突会在哈希表的另外一个空位置寻找。

//线性探测
while (_table[hashi]._state == EXIST)
{++hashi;hashi %= _table.size();
}_table[hashi]._kv = kv;
_table[hashi]._state = EXIST;
++_n;return true;
}

查找、删除

查找

返回结构体的指针利于后面的额删除

Hashdata<const K, V>* find(const K& key)
{HashFunc hf;size_t hashi = hf(key) % _table.size();while (_table[hashi]._state != EMPTY){if (_table[hashi]._state == EXIST&& _table[hashi]._kv.first == key){return (Hashdata<const K,V>*) & _table[hashi];}++hashi;hashi %= _table.size();}return nullptr;
}

删除

在删除的时候直接进行状态的修改

bool erase(const K& key)
{Hashdata<const K, V>* ret = find(key);if (ret){ret->_state = DELETE;--_n;return true;}return false;}

相关文章:

【C++】unordered系列

前言&#xff1a; 在C11及以后的标准中&#xff0c;unordered容器是标准模板库&#xff08;STL&#xff09;的一部分&#xff0c;提供了高效的数据结构选项&#xff0c;适用于需要快速查找和插入操作的场景。 unordered通常与关联容器一起使用&#xff0c;特别是unordered_map和…...

Cobbler 搭建方法

统信服务器操作系统行业版V20-1000c【Cobbler 搭建】手册 统信服务器操作系统行业版 V20版本上Cobbler 搭建方法 文章目录 功能概述一、使用范围二、cobbler工作流程1. Server 端2. Client 端三、 环境准备1. 测试环境告知,以提供配置时参考:2. 关闭防火墙、selinux:3. 注意…...

从边缘到云端,合宙DTURTU打造无缝物联网解决方案

随着物联网&#xff08;IoT&#xff09;技术的飞速发展&#xff0c;万物互联的时代已经到来&#xff0c; 如何高效、稳定地连接边缘设备与云端平台&#xff0c;实现数据的实时采集、传输与处理&#xff0c;成为了推动物联网应用落地的关键。 DTU&#xff08;数据传输单元&…...

【Android Studio】API 29(即Android 10)或更高版本,在程序启动时检查相机权限,并在未获取该权限时请求它

文章目录 1. 在AndroidManifest.xml文件中&#xff0c;声明相机权限&#xff1a;2. 在你的Activity中&#xff08;例如MainActivity&#xff09;测试 1. 在AndroidManifest.xml文件中&#xff0c;声明相机权限&#xff1a; <uses-feature android:name"android.hardwar…...

【裸机装机系列】3.kali(ubuntu)-更新sources.list并重启

当装机并重启计算机后&#xff0c;暂时还不能使用&#xff0c;需要更新源并下载软件 1、更新软件源 1> 切换root使用命令 sudo su root 进入界面后&#xff0c;是你自己的账户&#xff0c;不是root账户&#xff0c;这里的操作是需要进入root账户进行操作的&#xff0c;否…...

text2sql(NL2Sql)综述《The Dawn of Natural Language to SQL: Are We Fully Ready?》

《The Dawn of Natural Language to SQL: Are We Fully Ready?》(github)出自2024年6月的NL2SQL(Natural language to SQL )综述论文。这篇论文尝试回答如下三个问题&#xff1a; 问题1:NL2SQL的现状是什么&#xff1f;(Q1:Where Are we Now?) 论文图1总结了近20年NL2SQL方法…...

【滑动窗口】一题讲透滑动窗口!

&#x1f680;个人主页&#xff1a;一颗小谷粒 &#x1f680;所属专栏&#xff1a;力扣刷题 很荣幸您能阅读我的文章&#xff0c;诚请评论指点&#xff0c;欢迎欢迎 ~ 目录 1.1 题目要求 1.2 算法图解分析 1.3 代码实现 1.4 时间复杂度分析 1.5 算法思想总结 1.1 题目要…...

嵌入式通信原理—SPI总线通信原理与应用

文章目录 SPI 简介基本原理工作模式特点 SPI寻址方式1. 片选&#xff08;Chip Select, CS&#xff09;2. 多从设备通信3. 菊花链&#xff08;Daisy-Chain&#xff09;模式4. 地址寄存器&#xff08;应用层&#xff09; SPI通信过程时钟信号生成&#xff08;SCLK&#xff09;数据…...

基于web的 BBS论坛管理系统设计与实现

博主介绍&#xff1a;专注于Java .net php phython 小程序 等诸多技术领域和毕业项目实战、企业信息化系统建设&#xff0c;从业十五余年开发设计教学工作 ☆☆☆ 精彩专栏推荐订阅☆☆☆☆☆不然下次找不到哟 我的博客空间发布了1000毕设题目 方便大家学习使用 感兴趣的可以…...

【Scala入门学习】Scala的方法和函数

1. 方法 在scala中的操作符都被当成方法存在&#xff0c;比如说、-、*、/ 12就是1.(2)的调用&#xff0c; 2.0 是doule类型&#xff0c;强调用Int类型的写法为1.(2:Int) 1.1 方法的声明和使用 定义方法的语法&#xff1a; def 方法名([变量&#xff1a;变量类型&#xff…...

【JVM】概述

前言 Java的技术体系主要由支撑Java程序运行的虚拟机、提供各开发领域接口支持的Java类库、Java编程语言及许许多多的第三方Java框架&#xff08;如Spring、MyBatis等&#xff09;构成。在国内&#xff0c;有关Java类库API、Java语言语法及第三方框架的技术资料和书籍非常丰富&…...

鸿蒙开发笔记_电商严选02_登录页面跳转到我的页面、并传值

鸿蒙开发笔记整理,方便以后查阅! 由于上班较忙,只能抽空闲暇时间,快速整理更新中。。。 登录页面跳转到我的页面、并传值 效果图 我的设置页面 /*** 我的设置页面*/ import CommonConstants from ./CommonConstants import ItemData from ./ItemData import DataModel fr…...

clip论文阅读(Learning Transferable Visual Models From Natural Language Supervision)

目录 摘要训练pre-train model的过程将pre-train model应用于下游任务应用&#xff08;待更新&#xff09; 论文/项目地址&#xff1a;https://github.com/OpenAI/CLIP 提供了clip的pre-trained model的权重&#xff0c;也可安装使用pre-trained model 摘要 使用标签标注的图…...

用于图像分割的协 SMA Transformer:同多注意力转换器 !

在医学图像分割中&#xff0c;基于注意力机制和卷积神经网络的Transformer在提高性能方面起到了重要作用。然而&#xff0c;早期的模型往往在分割小而形状不规则的肿瘤时表现不佳。 为此&#xff0c;作者提出了一种基于SMA架构&#xff08;Synergistic Multi-Attention&#xf…...

lodash中_.difference如何过滤数组

_.difference(array, [values]) 作用&#xff1a; 创建一个具有唯一array值的数组&#xff0c;每个值不包含在其他给定的数组中。&#xff08;注&#xff1a;即创建一个新数组&#xff0c;这个数组中的值&#xff0c;为第一个数字&#xff08;array 参数&#xff09;排除了给…...

关于C# 数据库访问 转为 C++ CLI 数据库访问

Db_.cs 与 csharp_db.h功能是一样的。 Db_.cs /**************************************************************************************** 创建时间 &#xff1a;2006年12月19日文件名 &#xff1a;Db_.cs功能 &#xff1a;数据库…...

百度移动刷下拉词工具:快速出下拉词的技术分析

都2024年了&#xff0c;你还在做SEO百度下拉&#xff1f;答案当然是肯定的&#xff0c;虽然百度的搜索流量不如从前&#xff0c;但移动端的流量依然是巨大的&#xff01;除了百度SEO快排以外&#xff0c;下拉也是一大流量入口&#xff0c;尤其是在移动端搜索的流量越来越大时&a…...

学习笔记-Golang中的Context

文章目录 1、什么是Context2、Context的作用3、Context的解析3.1、Context的源码解析3.2、 context包中实现context接口的四种结构体类型3.2.1、emptyCtx3.2.2、cancelCtx3.2.3、timerCtx3.2.4、valueCtx 4、总结 1、什么是Context Context是 Go 语言中的一个标准库&#xff0…...

ArrayList 源码解析

ArrayList是Java集合框架中的一个动态数组实现&#xff0c;提供了可变大小的数组功能。它继承自AbstractList并实现了List接口&#xff0c;是顺序容器&#xff0c;即元素存放的数据与放进去的顺序相同&#xff0c;允许放入null元素&#xff0c;底层通过数组实现。除该类未实现同…...

libgit2编译

1. 源码下载 libgit2源码下载 2. 编译要求 CMake下载 CMake教程 3. 编译步骤 Prerequisites Make sure CMake on your %PATH% Build Create a build directory beneath the libgit2 source directory, and change into it: mkdir build && cd buildCreate the …...

数据结构之B树、B+树、B-树详解

B树、B树、B-树详解 目录 1. 引言2. B树&#xff08;B-Tree&#xff09; 2.1 定义2.2 特点2.3 操作2.4 应用场景 3. B树&#xff08;B Tree&#xff09; 3.1 定义3.2 特点3.3 操作3.4 应用场景 4. B-树&#xff08;B-Tree&#xff09; 4.1 定义4.2 特点4.3 操作4.4 应用场景 …...

掌握AI专著写作密码,优质工具介绍助你快速完成学术专著

学术专著创作难题与AI工具助力 写学术专著的挑战&#xff0c;除了“能够写出来”以外&#xff0c;还有“能够出版并获得认可”的难题。在出版行业中&#xff0c;学术专著的目标群体相对狭窄&#xff0c;出版社对选题的学术价值和作者的影响力有严格的要求&#xff0c;因此很多…...

OpenClaw隐私保护机制:Qwen3.5-9B-AWQ-4bit处理证件照自动打码

OpenClaw隐私保护机制&#xff1a;Qwen3.5-9B-AWQ-4bit处理证件照自动打码 1. 为什么需要自动化隐私保护 去年帮家人整理电子档案时&#xff0c;我遇到了一个棘手问题&#xff1a;上百张包含身份证、银行卡的照片需要手动打码。用PS一张张处理不仅耗时&#xff0c;还容易遗漏…...

如何用赛博朋克2077存档编辑器重塑你的夜之城体验

如何用赛博朋克2077存档编辑器重塑你的夜之城体验 【免费下载链接】CyberpunkSaveEditor A tool to edit Cyberpunk 2077 sav.dat files 项目地址: https://gitcode.com/gh_mirrors/cy/CyberpunkSaveEditor 在夜之城的霓虹灯下&#xff0c;你是否曾因错误的属性点分配而…...

告别拼接URL!手把手教你封装HarmonyOS的POST请求工具类

告别拼接URL&#xff01;手把手教你封装HarmonyOS的POST请求工具类 在HarmonyOS应用开发中&#xff0c;网络请求是每个开发者都无法绕开的核心功能。很多从Android转战HarmonyOS的开发者会发现&#xff0c;原本在Android中通过Retrofit等框架轻松实现的POST请求&#xff0c;在H…...

MacBook安装OpenClaw全记录:Phi-3-vision-128k-instruct多模态初体验

MacBook安装OpenClaw全记录&#xff1a;Phi-3-vision-128k-instruct多模态初体验 1. 为什么选择OpenClawPhi-3组合 去年第一次听说OpenClaw时&#xff0c;我就被这个"能直接操作电脑的AI助手"吸引了。作为一个经常需要处理多模态内容的创作者&#xff0c;传统AI工具…...

告别‘Setup is running...’卡死!保姆级PowerBuilder 9.0安装避坑指南(附安全模式备用方案)

PowerBuilder 9.0安装全攻略&#xff1a;从卡死困境到流畅部署的终极解决方案 如果你曾经在安装PowerBuilder 9.0时遭遇过"Setup is running..."的无限卡死&#xff0c;那么这篇文章就是为你量身定制的救星。作为一款经典的企业级开发工具&#xff0c;PowerBuilder至…...

DeepSeek-R1-Distill-Qwen-1.5B实战体验:边缘计算、手机助手的AI新选择

DeepSeek-R1-Distill-Qwen-1.5B实战体验&#xff1a;边缘计算、手机助手的AI新选择 1. 引言&#xff1a;小钢炮模型的崛起 在AI大模型领域&#xff0c;参数规模与计算资源需求一直是制约模型落地的关键瓶颈。当我们还在为动辄数十亿参数的大模型寻找合适算力时&#xff0c;De…...

Face3D.ai Pro零基础入门:5分钟从照片到3D人脸,小白也能玩转

Face3D.ai Pro零基础入门&#xff1a;5分钟从照片到3D人脸&#xff0c;小白也能玩转 1. 引言&#xff1a;从照片到3D人脸的魔法 想象一下&#xff0c;用手机随手拍一张自拍&#xff0c;5分钟后就能得到一个可以360度旋转的3D人脸模型。这不是科幻电影里的场景&#xff0c;而是…...

SEO宣传推广公司如何做好移动端优化

SEO宣传推广公司如何做好移动端优化 在当前数字化营销的浪潮中&#xff0c;移动端优化已经成为了每一个SEO宣传推广公司必须要掌握的技能之一。随着越来越多的用户通过手机浏览网站和进行在线购物&#xff0c;如何在移动端上获得更高的流量和转化率成为了企业竞争的关键。SEO宣…...