数据结构之哈希——学习笔记

今天看网课学习了哈希的数据结构,写下这一篇博客记录自己的学习过程。

1.哈希简介:

 

我们发现某些时候映射到小集合的时候会同时有多个值映射到一个下标里面,所以接下来是这种情况的解决方案1: 

 我们考虑当两个数字映射之后的结果是在同一个下标的时候,那么不妨可以将第二个映射到这个下标的数字往后移动到第一个空白的下标里面。

实际上上面这一种解决问题的方式存在较大的问题,当冲突之后后移的话会导致对应下标里面的值不再是本身应该映射到这个下标里面的值了。

所以考虑到第一种值冲突解决问题在有些情况的不适用,那么接下来介绍第二种值冲突的解决方案:

接下来详细介绍vector(可以理解为动态数组): 

这样的方法可以理解为开设了多个链表,每个下标都相当于是一条链表,实际上虽然这种方法已经解决了绝大多数的问题但是当遇见特殊的样例,也就是样例映射之后全部都在一个下标的时候,一样是存在问题的。

接下来看一下哈希函数的设计:

 接下来看一下字符串如何进行哈希操作:

另外请思考: 

令base为11会导致值冲突加剧,另外发生值冲突我们考虑双哈希甚至三哈希等多次哈希操作来解决,也就是设置多个base以及p的值,这样的话只有当多组的base和p计算出来的值都相同的时候我们才会认为两个字符串相同。

 接下来看一下c++中自带的hash:

接下来来看一些例题:

 代码如下:

#include<bits/stdc++.h>
using namespace std;
int n,m;
const int P=9999971;//要模的素数
int a[200001],b[200001];
vector<int>c[P]; 
int main(){cin>>n>>m;//存下两篇论文的长度for(int i=0;i<P;i++)//将所有的链表数组清空c[i].clear();for(int i=1;i<=n;i++){cin>>a[i];c[a[i]%P].push_back(a[i]);//存下第一篇论文中所有的数字}int x=0;for(int i=1;i<=m;i++){cin>>b[i];bool ok=false;//假设这个数字不是抄袭的int v=b[i]%P;int l=c[v].size();//判断假设是否成立for(int j=0;j<l && !ok;j++)if(c[v][j]==b[i]) ok=true;if(ok) ++x;//如果成立 抄袭的部分加一}//判断被标记的抄袭的论文部分是否大于了一半if(2*x>=m) cout<<"Yes"<<endl;else cout<<"No"<<endl;return 0;
}

这里还有一种使用map的方法:

#include<bits/stdc++.h>
using namespace std;
int n,m;
const int P=9999973;
int a[200001],b[200001];
unordered_map<int,int>c;
int main(){cin>>n>>m;c.clear();for(int i=1;i<=n;i++){cin>>a[i];c[a[i]]=1;}int x;for(int i=1;i<=m;i++){cin>>b[i];if(c.find(b[i]) != c.end()) ++x;}if(x*2>=m) cout<<"Yes"<<endl;else cout<<"No"<<endl;return 0;
}

接下来再看第二个题:

 很明显这里是使用map,这是我的代码:

#include<bits/stdc++.h>
using namespace std;
int n,m;
unordered_map<string,int>a;
unordered_map<string,int>b;
unordered_map<string,int>c;
int main(){cin>>n>>m;a.clear();b.clear();c.clear();for(int i=1;i<=n;i++){string s;cin>>s;int x,y,z;cin>>x>>y>>z;a[s]=x;b[s]=y;c[s]=z;}for(int i=1;i<=m;i++){string s;cin>>s;if(a.find(s)==a.end()) cout<<"-1"<<' '<<"-1"<<" "<<"-1"<<endl;else cout<<a[s]<<' '<<b[s]<<' '<<c[s];}return 0;
}

但是会发现上面的代码使用了三个map来分别存身高年龄专业编码,实际上这三个都可以通过一个结构体来存储:

#include<bits/stdc++.h>
using namespace std;
int n,m;
struct Info{int x,y,z;
};
unordered_map<string,Info>a;
int main(){cin>>n>>m;a.clear();for(int i=1;i<=n;i++){string s;cin>>s;Info temp;cin>>temp.x>>temp.y>>temp.z;a[s]=temp;}for(int i=1;i<=m;i++){string s;cin>>s;if(a.find(s) != a.end()) cout<<a[s].x<<' '<<a[s].y<<' '<<a[s].z<<endl;else cout<<"-1"<<' '<<"-1"<<' '<<"-1"<<endl;}return 0;
}

ok,接下来看下一道题目:

#include<bits/stdc++.h>
using namespace std;
int n;
unordered_map<int,int>c;
int a[200001];
int main(){scanf("%d",&n);c.clear();for(int i=1;i<=n;i++){int x;cin>>x;++c[x];}int x=0,l=0;for(auto temp : c){if(temp.second>x){x=temp.second;l=0;}if(temp.second==x) a[++l]=temp.first;}sort(a+1,a+l+1);for(int i=1;i<=l;i++)cout<<a[i]<<' ';return 0;
}

 这道题目看似很简单实则还是有一定难度的。正常人思路肯定一开始都是利用数组来存储每个数字出现的次数然后最后遍历数组容量,更新出现次数最多的数字,如果遇上多个相同大的,那就利用一个数组和一个判断长度l的变量来进行不断更新和便于之后的输出。

接下来看第四题:

 代码如下:

#include<bits/stdc++.h>
using namespace std;
int n;
unordered_map<int,int>c;
int main(){cin>>n;c.clear();for(int i=1;i<=n;i++){int x;cin>>x;++c[x];}int x=0;bool add=false;for(auto temp : c){if(temp.second & 1) add=true;x+=temp.second/2*2;}if(add) ++x;cout<<x<<endl;return 0;
}

最后一个题目了:

 代码如下:

#include<bits/stdc++.h>
using namespace std;
int n,m;
const int p=9999973,base=101;
int ha[200010],hb[200010],c[200010];
char a[200010],b[200010];
int main(){scanf("%d%d",&n,&m);scanf("%s%s",a+1,b+1);c[0]=1;for(int i=1;i<=200000;i++)c[i]=c[i-1]*base%p;for(int i=1;i<=n;i++)ha[i]=(ha[i-1]*base+(a[i]-'a'))%p;for(int i=1;i<=m;i++)hb[i]=(hb[i-1]*base+(b[i]-'a'))%p;int ans=0;for(int i=1;i+m-1<=n;i++)if((ha[i+m-1]-1LL*ha[i-1]*c[m]%p+p)%p==hb[m])++ans;printf("%d\n",ans);return 0;
}

以上是一个单哈希的写法,c数组代表了base的i次方的值,而ha和hb分别包含了长度为i子串的哈希值最后一个for循环进行遍历计算有b子串在a子串出现了多少次。然后输出答案,接下来介绍一个双哈希的写法:

#include<bits/stdc++.h>
using namespace std;
int n,m;
const int p=9999973,base=101;
const int p2=9999973,base2=137;
int ha[200010],hb[200010],c[200010],c2[200011],ha2[200011],hb2[200011];
char a[200010],b[200010];
int main(){scanf("%d%d",&n,&m);scanf("%s%s",a+1,b+1);c[0]=1;c2[0]=1;for(int i=1;i<=200000;i++){c[i]=c[i-1]*base%p;c2[i]=c2[i-1]*base2%p2;}for(int i=1;i<=n;i++){ha[i]=(ha[i-1]*base+(a[i]-'a'))%p;ha2[i]=(ha2[i-1]*base2+(a[i]-'a'))%p2;}for(int i=1;i<=m;i++){hb[i]=(hb[i-1]*base+(b[i]-'a'))%p;hb2[i]=(hb2[i-1]*base2+(b[i]-'a'))%p2;}int ans=0;for(int i=1;i+m-1<=n;i++)if((ha[i+m-1]-1LL*ha[i-1]*c[m]%p+p)%p==hb[m] && (ha2[i+m-1]-1LL*ha2[i-1]*c2[m]%p2+p2)%p2==hb2[m])++ans;printf("%d\n",ans);return 0;
}

希望今天的学习记录笔记同样对读者有所帮助。

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

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

相关文章

FastDFS

docker 安装 1拉取镜像&#xff08;已经内置Nginx&#xff09; docker pull delron/fastdfs 2 构建Tracker # 22122 > Tracker默认端口 docker run --nametracker-server --privilegedtrue -p 22122:22122 -v /var/fdfs/tracker:/var/fdfs -d delron/fastdfs tracker 3 …

【ESP32接入语言大模型之通义千问】

1. 通义千问 讲解视频&#xff1a; ESP32接入语言大模型之通义千问 随着人工智能技术的不断发展&#xff0c;自然语言处理领域也得到了广泛的关注和应用。通义千问由阿里云开发&#xff0c;目标是帮助用户获得准确、有用的信息&#xff0c;解决他们的问题和困惑&#xff0c;也…

数据库 补充 树,红黑树,b树,b+树

01.树 02.二叉树和二叉平衡树 03.平衡二叉树的恢复 将导致不平衡的结点称作被破坏者&#xff0c;破坏了结点的平衡的结点成为破坏者&#xff0c;经过调整可以让该树平衡的结点称为调整结点。 LL型&#xff1a; 以被破坏者的左孩子结点作为调整结点&#xff0c;对其进行右旋…

C# Attribute特性实战(1):Swtich判断优化

文章目录 前言简单Switch问题无参Swtich方法声明Swtich Attribute声明带有Swtich特性方法主方法结果 有参Switch修改代码修改运行过程运行结果 总结 前言 在经过前面两章内容的讲解&#xff0c;我们已经简单了解了如何使用特性和反射。我们这里解决一个简单的案例 C#高级语法 …

WPF美化ItemsControl1:不同颜色间隔

首先我们有的是一个绑定好数据的ItemsControl <ItemsControl ItemsSource"{Binding Starts}"> </ItemsControl> 运行后呢是朴素的将数据竖着排列 如果想要数据之间有间距&#xff0c;可以使用数据模板&#xff0c;将数据放到TextBlock中显示&#xff0…

深度学习(Pytorch版本)

零.前置说明 1、code 2、视频 数据预处理实现_哔哩哔哩_bilibili

回归模型代码实现

回归模型代码实现 1.多元函数线性回归w的求法 import numpy as np# 定义一组自变量&#xff0c;每条数据最后一列为b x np.array([[1,1,1,1],[1,2,3,1],[2,2,4,1],[2,3,5,1]])# 定义w&#xff0c;其中b的值为0.5 y np.dot(x,np.array([2,4,6,0.5])) x_x_1 np.linalg.inv(n…

【2023 CCF 大数据与计算智能大赛】基于TPU平台实现超分辨率重建模型部署 基于Real-ESRGAN的TPU超分模型部署

2023 CCF 大数据与计算智能大赛 《基于TPU平台实现超分辨率重建模型部署》 洋洋很棒 李鹏飞 算法工程师 中国-烟台 2155477673qq.com 团队简介 本人从事工业、互联网场景传统图像算法及深度学习算法开发、部署工作。其中端侧算法开发及部署工作5年时间。 摘要 本文是…

超维空间M1无人机使用说明书——31、基于模板匹配的物体识别功能

引言&#xff1a;ROS提供的物体识别功能包find_object_2d&#xff0c;该功能包用起来相对简单&#xff0c;只需要简单进行模板匹配即可。需要接显示器进行模板训练&#xff0c;远程比较卡&#xff0c;不建议 一、功能包find_object_2d简介 ROS的优点之一是有大量可以在应用程…

【React系列】Redux(一)管理状态

本文来自#React系列教程&#xff1a;https://mp.weixin.qq.com/mp/appmsgalbum?__bizMzg5MDAzNzkwNA&actiongetalbum&album_id1566025152667107329) 在React的开发过程中&#xff0c;Redux对于我们是非常重要的。 但是对于很多人来说&#xff0c;初次接触redux会感觉r…

基于SSM的人事档案管理系统的设计与实现

末尾获取源码 开发语言&#xff1a;Java Java开发工具&#xff1a;JDK1.8 后端框架&#xff1a;SSM 前端&#xff1a;采用JSP技术开发 数据库&#xff1a;MySQL5.7和Navicat管理工具结合 服务器&#xff1a;Tomcat8.5 开发软件&#xff1a;IDEA / Eclipse 是否Maven项目&#x…

1.大数据概述

目录 概述hadoophadoop 模块hadoop 发行版apache社区版本CDP(CDHHDP)其它云产商框架选择 hadoop 安装 结束 概述 先了解几个常用的网站 apache 官网hadoop 官网hadoop githubhttps://github.com/apache/xxx [https://github.com/apache/spark (example)] hadoop hadoop 模块…

ssm基于web的网络游戏交易平台信息管理系统的设计与实现论文

摘 要 传统办法管理信息首先需要花费的时间比较多&#xff0c;其次数据出错率比较高&#xff0c;而且对错误的数据进行更改也比较困难&#xff0c;最后&#xff0c;检索数据费事费力。因此&#xff0c;在计算机上安装网络游戏交易平台软件来发挥其高效地信息处理的作用&#x…

基于帝国主义竞争算法优化的Elman神经网络数据预测 - 附代码

基于帝国主义竞争算法优化的Elman神经网络数据预测 - 附代码 文章目录 基于帝国主义竞争算法优化的Elman神经网络数据预测 - 附代码1.Elman 神经网络结构2.Elman 神经用络学习过程3.电力负荷预测概述3.1 模型建立 4.基于帝国主义竞争优化的Elman网络5.测试结果6.参考文献7.Matl…

【Java 进阶篇】Nginx 使用详解:搭建高性能的 Web 服务器

在互联网的世界里&#xff0c;Web 服务器是我们访问网站、获取信息的入口。Nginx&#xff08;发音"engine x"&#xff09;作为一款轻量级、高性能的 Web 服务器和反向代理服务器&#xff0c;因其出色的性能和可扩展性而备受推崇。本文将围绕 Nginx 的使用进行详解&am…

数据结构学习 jz56数组中数字出现的次数

关键词&#xff1a;位运算 异或性质 虽然有两道题&#xff0c;但是其实应该分成三个级别的题目。 题目一&#xff1a; 一个整型数组 sockets 里除 一个 数字之外&#xff0c;其他数字都出现了两次。 思路&#xff1a;异或的性质 复杂度计算&#xff1a; 时间复杂度O(n) 空…

Python字符串

目录 1 创建字符串的三种方式2 字符串的转义3 字符串的格式化输出4 字符串的索引5 字符串的切片6 字符串的拼接7 计算字符串的长度8 判断字符串是否存在 字符串是编程中经常使用到的概念&#xff0c;熟悉字符串的常见用法是掌握编程的必经之路&#xff0c;本篇介绍一下字符串的…

ASP.NET Core高级之认证与授权(一)--JWT入门-颁发、验证令牌

阅读本文你的收获 了解认证和授权的作用了解在ASP.NET Core中实现身份认证的技术都有哪些学习基于JWT认证并学会颁发和验证JWT令牌 一、重要的前置概念 在一个系统中&#xff0c;不是所有的功能和资源都能够被自由地访问&#xff0c;比如你存在银行系统里面的资金&#xff0c…

网络故障问题一般性检查排查思路

一、基本连通性检查 在网络中ping是一个十分强大的TCP/IP工具。它可以用来检测网络的连通情况和分析网络速度、也可以ping网址根据域名得到服务器IP、同时我们根据ping返回的TTL值来判断对方所使用的操作系统及数据包经过路由器数量。 ping 网址&#xff0c;有几种输出情况&a…

Linkage Mapper 工具参数详解——Centrality Mapper

【小白一学就会无需其他教程】此文档用于解析使用Linkage Mapper 各输入输出参数详情以及可能的影响&#xff0c;并介绍了如何解释模型输出结果和输出参数&#xff0c;适合刚入手的人。篇幅很长很啰嗦&#xff0c;是因为每个参数都解释的万分细致。 从以下链接中获取内容&…