- 周一直播
- 哈希表
- 定义:哈希表通过建立「键key」和「值value」之间的映射,实现高效的元素查找。python对应是dict()
- 注意:哈希表dict()是一个字典,键必须是唯一的,但值则不必。用来存放数组的元素值以及索引值d = {key1 : value1, key2 : value2, key3 : value3 }
- 注意:哈希表的value不一定是一个值,可能是一个数组,包含很多部分...
- 访问哈希表(字典)中的key/value,d.keys () / d.values()
- 给哈希表赋值/获取key1对应的value值可以用d[key1] = value1 / d[key1]
- key in dict 如果键在字典dict里返回true,否则返回false
- 注意:哈希集合set()是一个集合,其中的元素是不重复的,转换为列表时用list(set(s))
- 在哈希表中添加元素用s.add(),删除用del s[key]
- 将数组s转换为哈希集合set(s)
- 输入一个key,在哈希表中查询并获取value,时间复杂度为O(1)。

- 映射map是一组键值对的结构,具有极快的查找速度。
- 集合set是一组key的集合,但不存储value。由于key不能重复,所以,在set中,没有重复的key。
- (1)哈希集合set在【判断重复元素】以及【数组去重】上的应用
- LeetCode 217、存在重复元素
- 遍历数组,判断当前的元素是否在set中
- LeetCode 349、两个数组的交集
- 将一个数组转换为哈希集合,遍历另一个数组元素,只要在前一个数组的哈希集合中,就add进去结果set中。
- 【哈希集合】科大讯飞2023非凡计划-禁着点的方案数
- 由于题目要求x和y均为正整数,且需要满足x+y = s的条件,故x和y的的取值范围均为[1, s-1]。
- 我们可以用一个哈希集合hash_set来储存禁着点,遍历x在[1, s-1]中的取值,并且计算y = s-x,若此时x和y均不位于哈希集合hash_set中,则方案数+1。
- 输入形式:hash_set = set(map(int, input().split()))
- 【哈希集合】贝壳2021秋招-牛妹的字符串
- 先记录所有出现过的字母的哈希集合,再取前k个作为待删除的哈希集合,然后再次遍历原字符串s,若其不出现在待删除的哈希集合中,则将其加入到ans中
- LeetCode 217、存在重复元素
- (2)哈希表在【下标查询】类型题目中的应用
- 一般来说,都是将数组元素的值作为key,它的索引作为value
- LeetCode 1、两数之和
- target - 当前值 = 我们需要找到的另一个值,注意这里哈希表中的key=数的值,value=数的下标
- LeetCode 219、存在重复元素II
- 判断当前访问的元素是否存在于哈希表中,并且它们索引之间的距离小于k,满足条件就返回True,不满足就将这个元素加入到哈希表中(哈希表的使用也有效的更新了满足前一条件而不满足后一条件的情况)
- (3)哈希表在【元素配对】类型题目中的应用
- LeetCode 205、同构字符串
- 法一:设置两个哈希表,key是s的元素值,value是t的元素值,判断每个哈希表中的元素是否配对。

- 法二:设置两个哈希表,判断每个哈希表中对应元素的value(即原数组元素的索引)是否相同,如果不同,说明对应位置无法配对,那就返回false。这个需要遍历两边,第一遍给哈希表赋值,第二遍开始遍历比较
- class Solution:
- def isIsomorphic(self, s: str, t: str) -> bool:
- # 设置一个哈希集合用来存储字符串 s 当中的元素的索引
- dic1 = {}
- # 设置一个哈希集合用来存储字符串 t 当中的元素的索引
- dic2 = {}
- for i in range(len(s)):
- dic1[s[i]] = i
- dic2[t[i]] = i
- for i in range(len(s)):
- if dic1[s[i]] != dic2[t[i]]:
- return False
- return True
- for i in range(len(s)):
- class Solution:
- 法一:设置两个哈希表,key是s的元素值,value是t的元素值,判断每个哈希表中的元素是否配对。
- LeetCode 205、同构字符串
- (4)哈希表在【统计元素频率】类型题目中的应用
- LeetCode 242、有效的字母异位词
- 看到 频次 这个词,你脑海中第一想法是什么?
- 没错,就是 哈希表 !
- 两种解法:
- 法一:哈希表法 自己的(优势在于可以比较非字母的字符)
- 分别遍历s和t,统计其中的元素和频率
- 然后再遍历s,将s中的key的value和t的进行比较
- 法二:数组统计法 吴师兄的
- 解法思路很简单。
- 1、首先先判断两个字符串长度是否相同,不相同直接返回 false
- 2、然后把 s 中所有的字符出现个数使用 计数器 统计起来,存入一个大小为 26 的数组中(注意题目的说明)
- 3、最后再来统计 t 字符串,即遍历 t 时将对应的字母频次进行减少,如果期间 计数器 出现小于零的情况,则说明 t 中包含一个不存在于 s 中的字母,直接返回 false。
- 4、最后检查计数器是否归零。
- LeetCode 383、赎金信(HJ81. 字符串字符匹配)
- 和242异曲同工,也可以用法一来做,判断dic1里面的元素是否在dic2里面存在,同时它的value(即出现的频次)<=dic2的
- LeetCode 387、字符串中的第一个唯一字符
- 用哈希表统计每个字符出现的频率,再去遍历字符串,找到第一个不重复字符的索引
- 统计可以使用哈希表手动,也可以使用Counter函数,返回的也是一个哈希表
- from collections import Counter # s = "leetcode"
- c = Counter(s) # Counter({'e': 3, 'l': 1, 't': 1, 'c': 1, 'o': 1, 'd': 1})
- LeetCode 409、最长回文串
- 组成哈希频率表,然后访问哈希表中的values,用.values()
- 如果字母是偶数,那么最大可以使用这个偶数次,如果是奇数,则最大可以使用奇数次-1次
- 最后判断一下,如果结果的长度小于数组长度,说明在中间还能放一个,结果=结果+1
- LeetCode 242、有效的字母异位词
- 哈希表
- 周二直播
- 【哈希表】美团2023秋招-小美的排列询问
- 一次遍历数组,判断是否有和x、y相等并且相连即可。
- 可优化逻辑:因为x和y是后输入的,必须存储整个数组,但是上面说了 排列是指一个长度为n的数组,其中 1 到n 每个元素恰好出现一次。构建哈希表,用哈希表储存x和y的下标,判断下标是否相差1即可
- 【哈希表】小红书2023秋招-推荐系统
- 哈希+排序,将每个单词先存入哈希表中统计频率,然后根据频率对哈希的key排序(如果频率相同按照字典序排序),返回前三个。
- 具体流程为:
- 将输入的字符串按空格分割成单词数组。
- 使用HashMap统计每个单词的出现次数。
- 将HashMap的键(单词)转换为列表。
- 对列表中的单词按照词频从高到低进行排序。如果词频相同,则按照字典序进行排序。
- 遍历排序后的列表,打印出现次数超过3的热搜单词。
- 排序使用lambda匿名函数,这里涉及到# 对ans进行排序,先根据频率从高到底进行排序,即以-item[1]为第一个排序依据# 频率相同的单词,再以单词字典序即item[0]作为排序依据
- ans.sort(key = lambda item: (-item[1], item[0]))
- 【哈希表】阿里淘天2023秋招-讨厌鬼的排列
- 先用哈希表cnt储存所有正数的出现频率。
- 首先考虑长度为1的排列,显然只有{1}是符合要求的,故长度为1的排列的个数为cnt[1]。
- 接着考虑长度为2的排列,显然{1,2}和{2,1}符合要求,且不同位置的2或1可以视为两个不同的组合,故根据乘法原理,长度为2的排列的个数为cnt[1]*cnt[2]。
- 以此类推,若考虑长度为m的排列时,若数字1到m的出现频率均不为0,那么长度为m的排列的个数为cnt[1]*cnt[2]*...*cnt[m-1]*cnt[m]。
- 故本题使用哈希表以及乘法原理即可解决。
- 【哈希表】阿里2023春招实习-合法的三元组
- 数学题
- 三元组(ai,aj,ak) 要满足 max(ai,aj,ak) − min(ai,aj,ak) = 1,那么这三个数可能是以下两种情况
- a+1, a+1, a
- a+1, a, a
- 其中a为任意整数
- 故我们使用哈希表cnt统计所有元素出现的频率。对于任意整数a,若已知cnt[a]和cnt[a+1],
- 1、a+1, a+1, a的情况。那么cnt[a]至少为1,cnt[a+1]至少为2,要在所有的a+1中挑选出2个具体的a+1,由排列组合定理可知组合数为cnt[a+1]*(cnt[a+1]-1)//2,再根据乘法定理可知总的挑选组数为cnt[a]cnt[a+1](cnt[a+1]-1)//2
- 2、a+1, a, a的情况。那么cnt[a+1]至少为1,cnt[a]至少为2,要在所有的a中挑选出2个具体的a,由排列组合定理可知组合数为cnt[a]*(cnt[a]-1)//2,再根据乘法定理可知总的挑选组数为cnt[a+1]cnt[a](cnt[a]-1)//2
- 遍历cnt中的所有key,进行判断和累加即可完成题目。
- 【哈希表】美团2023秋招-小美的排列询问
- 周三作业
- 【哈希集合】华为2023秋招-获取连通的相邻节点列表
- 题目要求找出与节点A相邻的节点,由于题目中“连通”的定义是指两个节点拥有相同的VLAN_ID,而不是指图论上节点的连通,故无需使用任何搜索算法来完成。
- 因此我们只需要先用哈希集合VLAN_ID_A_set储存节点A的所有VLAN_ID,然后再遍历所有剩余节点,查看每一个节点的VLAN_ID是否位于哈希集合VLAN_ID_A_set中即可。
- 【哈希表】2023B-斗地主
- 注意删去2和大小王"B"、"C"
- 注意顺子的序列为:i-cur_length, ..., i-3, i-2, i-1
- 注意数字i被用完的情况,即在cnt_using_num中的值为4
- 之所以把15也加入考虑
- 是因为i取14时,若没有仍然可以延长cur_length
- 会进入else中的分支,而无法实现ans的更新
- 【哈希表】2023B-单词接龙
- 模拟题+哈希表,需要注意排序问题
- 构建一个哈希表,用于按照单词首字母储存单词列表
- key为某一个首字母first_ch,value为字母first_ch为首字母的单词列表
- 什么时候无法找到接龙单词?ans的末尾字母ans[-1],在dic中对应的单词列表长度为0
- 简答题
- 哈希集合和哈希表有什么区别和联系?
- 哈希表dict()是一个字典,键必须是唯一的,但值则不必。用来存放数组的元素值以及索引值d = {key1 : value1, key2 : value2, key3 : value3 }
- 哈希集合set()是一个集合,其中的元素是不重复的,转换为列表时用list(set(s))
- 什么是可哈希(hashable)的数据类型,什么是不可哈希(unhashable)的数据类型?请分别举出例子。
- 可哈希(hashable)的数据类型是指在创建后其值不可变,且能够通过哈希函数映射到一个固定的哈希值的数据类型。这使得可哈希对象在集合(例如集合、字典等)中被用作键(key),因为键需要具有唯一性。
- 不可哈希(unhashable)的数据类型是指在创建后其值可以变化,或者无法通过哈希函数映射到一个固定的哈希值的数据类型。
- 可哈希对象通常是不可变的,可以用作字典的键或集合的成员。如整数、字符串、元组
- 不可哈希对象通常是可变的,不能用作字典的键或集合的成员,但它们可以作为字典的值。如列表、字典、集合
- 你可以归纳出哈希表在算法题中的几种常见适用场景吗?
- 【下标查询】
- 【元素配对】
- 【统计元素频率】
- 哈希集合和哈希表有什么区别和联系?
- 【哈希集合】华为2023秋招-获取连通的相邻节点列表
哈希表学习笔记——第13-15天内容
最新推荐文章于 2024-12-31 01:03:23 发布
本文围绕Python中的哈希表和哈希集合展开,介绍了它们的定义、操作及时间复杂度。详细阐述了哈希集合在判断重复元素、数组去重等方面的应用,以及哈希表在下标查询、元素配对、统计元素频率等算法题中的常见场景,并结合多道LeetCode和大厂笔试题进行说明。


3065

被折叠的 条评论
为什么被折叠?



