【算法系列】哈希表
目录
哈希表总结
leetcode题目
一、两数之和
二、判定是否互为字符重排
三、存在重复元素
四、存在重复元素 II
五、字母异位词分组
六、在长度2N的数组中找出重复N次的元素
七、两个数组的交集
八、两个数组的交集 II
九、两句话中的不常见单词
哈希表总结
1.存储数据的容器
2.需要快速查找数据时,用哈希表
3.当题目中给定的字符串或者数组只包含小写字母或数据范围是0~100/1000等等时,可以用数组模拟哈希表
4.当数据范围是负数到正数时,不建议用数组模拟哈希表,因为还要加一个数转化之后进行映射,建议直接使用STL容器
leetcode题目
一、两数之和
1. 两数之和 - 力扣(LeetCode)https://leetcode.cn/problems/two-sum/1.题目解析
给定数组与target, 返回和为target的两个元素下标
2.算法分析
解法一: 暴力枚举
策略一: 先固定一个数,然后依次与该数之后的数相加
策略二: 先固定一个数,然后依次与该数之前的数相加
解法二: 使用哈希表优化
暴力解法之所以慢,以策略二为例, 是因为枚举到nums[i]时,要在这个位置之前都遍历一下,看哪个数字等于target-nums[i], 所以如果我们枚举到nums[i]时,前面的数字都被扔进了哈希表中,我们就可以以O(1)的时间复杂度找到结果~
注意:如果是用哈希表暴力枚举策略一,最好是倒着遍历~
3.算法代码
暴力枚举策略一:
class Solution {
public:vector<int> twoSum(vector<int>& nums, int target) {for(int i = 0; i < nums.size(); i++){for(int j = i + 1; j < nums.size(); j++){if(nums[i] + nums[j] == target)return {i, j}; }}return {-1, -1};}
};
暴力枚举策略二:
class Solution {
public:vector<int> twoSum(vector<int>& nums, int target) {for(int i = 1; i < nums.size(); i++){for(int j = i - 1; j >= 0; j--){if(nums[i] + nums[j] == target)return {i, j}; }}return {-1, -1};}
};
哈希表优化策略一:
class Solution {
public:vector<int> twoSum(vector<int>& nums, int target) {unordered_map<int, int> hash; //<nums[i], i>for(int i = nums.size()-1; i >= 0; i--){int x = target - nums[i];if(hash.count(x)) return {hash[x], i};hash[nums[i]] = i;}return {-1, -1}; //照顾编译器}
};
哈希表优化策略二:
class Solution {
public:vector<int> twoSum(vector<int>& nums, int target) {unordered_map<int, int> hash; //<nums[i], i>for(int i = 0; i < nums.size(); i++){int x = target - nums[i];if(hash.count(x)) return {hash[x], i};hash[nums[i]] = i;}return {-1, -1}; //照顾编译器}
};
二、判定是否互为字符重排
面试题 01.02. 判定是否互为字符重排 - 力扣(LeetCode)https://leetcode.cn/problems/check-permutation-lcci/1.题目解析
给定两个字符串,判断一个字符串是否能够通过重排变成另一个字符串
2.算法分析
如果s1能够重排形成s2, 那么s1每个字符出现的个数和s2对应字符出现的个数是相等的!于是可以使用哈希表,而题目中说字符串只有小写字母,因此用数组模拟哈希表即可。所以解法就是用两个哈希表,然后判断哈希表是否相等即可;
优化1: 只使用一个哈希表统计s1中字符个数,然后遍历第二个字符串,把对应字符在哈希表中的个数--, 如果--之后是负数了,返回false即可
优化2: 两个字符串的长度不相等,直接返回false即可
3.算法代码
class Solution {
public:bool CheckPermutation(string s1, string s2){//优化if(s1.size() != s2.size()) return false;int hash[26] = {0};for(auto& e : s1) hash[e - 'a']++;for(auto& e : s2){hash[e - 'a']--;if(hash[e - 'a'] < 0)return false;}return true;}
};
三、存在重复元素
217. 存在重复元素 - 力扣(LeetCode)https://leetcode.cn/problems/contains-duplicate/1.题目解析
数组中存在重复元素返回true, 不存在重复元素返回false
2.算法分析
使用哈希表解决问题~
3.算法代码
unordered_map:
class Solution {
public:bool containsDuplicate(vector<int>& nums) {unordered_map<int, int> hash;for(auto& e : nums){hash[e]++;if(hash[e] > 1) return true;}return false;}
};
unordered_set:
class Solution {
public:bool containsDuplicate(vector<int>& nums) {unordered_set<int> hash;for(auto& e : nums){if(hash.count(e)) return true;elsehash.insert(e);}return false;}
};
四、存在重复元素 II
219. 存在重复元素 II - 力扣(LeetCode)https://leetcode.cn/problems/contains-duplicate-ii/1.题目解析
判断数组中是否存在两个相同的元素,并且下标的绝对值小于等于k
2.算法分析
从前向后遍历数组,同时将遍历过的元素和下标绑定扔进哈希表,遍历的同时判断是否满足题意即可
小细节:nums = [1 0 2 1 3 1 4], k =2, 当遍历到第2个1时,发现下标i-j=3>k, 不满足题意,此时将1和下标3绑定扔进哈希表覆盖之前的 <1, 0> 是完全可以的, 因为题目求的是 i-j <= k, 因此i和j越近越好,因此我们可以直接覆盖原先的值~
3.算法代码
class Solution {
public:bool containsNearbyDuplicate(vector<int>& nums, int k) {unordered_map<int, int> hash; // <nums[i], i>for(int i = 0; i < nums.size(); i++){if(hash.count(nums[i]) && i-hash[nums[i]] <= k)return true;hash[nums[i]] = i;}return false;}
};
五、字母异位词分组
49. 字母异位词分组 - 力扣(LeetCode)https://leetcode.cn/problems/group-anagrams/description/1.题目解析
给一个字符串数组,将所有的字母异位词放到一组,返回一个二维数组
2.算法分析
1.判断两个字符串是否是字母异位词(可以用哈希表,但是代码不好写,我们选择直接排序, 排序结果一样,那就互为字母异位词)
2.将相同的字母异位词分组 --- 借助哈希表 <string, string[ ]>, 哈希表第一个位置存储排序后的字符串,第二个存储一个字符串数组;
3.算法代码
class Solution {
public:vector<vector<string>> groupAnagrams(vector<string>& strs) {unordered_map<string, vector<string>> hash;//1.将所有的字母异位词分组for(auto& s : strs){string tmp = s;sort(tmp.begin(), tmp.end());hash[tmp].push_back(s);}//2.提取结果vector<vector<string>> ret;for(auto& [x, y] : hash){ret.push_back(y);}return ret;}
};
六、在长度2N的数组中找出重复N次的元素
961. 在长度 2N 的数组中找出重复 N 次的元素 - 力扣(LeetCode)https://leetcode.cn/problems/n-repeated-element-in-size-2n-array/description/1.题目解析
我们在深剖一下题意,本质就是只有1个数重复出现了,其他数都只出现了一次
2.算法分析
思路一: 遍历数组,将当前元素和出现次数丢进哈希表,当某个数出现次数 == n时,返回该数
思路二: 遍历数组,进循环先判断该数是否已经存在,存在就直接返回,不存在就将该数丢进哈希表
3.算法代码
思路一:
class Solution {
public: int repeatedNTimes(vector<int>& nums) { size_t n = nums.size() / 2;unordered_map<int, int> hash; // [x, count] for(auto& e : nums) { hash[e]++; if(hash[e] == n) return e; } return -1;}
};
思路二:
class Solution {
public: int repeatedNTimes(vector<int>& nums) { unordered_map<int, int> hash; // [x, count] for(auto& e : nums) { if(hash[e] == 1) // 只需要检查是否已经存在(即重复了一次) return e; hash[e]++; } return -1;}
};
七、两个数组的交集
349. 两个数组的交集 - 力扣(LeetCode)https://leetcode.cn/problems/intersection-of-two-arrays/submissions/
1.题目解析
返回两个数组的交集(输出结果的每个元素要是唯一的)
2.算法分析
将两个数组元素扔进两个 unordered_set 哈希表进行去重,然后遍历其中一个哈希表,看该哈希表中的元素在另一个哈希表中是否存在,存在就插入到结果数组中!
3.算法代码
class Solution {
public:vector<int> intersection(vector<int>& nums1, vector<int>& nums2) {vector<int> ret;unordered_set<int> hash1;unordered_set<int> hash2;for(auto& e : nums1) //对nums1元素去重hash1.insert(e);for(auto& e : nums2) //对nums2元素去重hash2.insert(e);for(auto& e : hash1)if(hash2.count(e))ret.push_back(e);return ret;}
};
八、两个数组的交集 II
350. 两个数组的交集 II - 力扣(LeetCode)https://leetcode.cn/problems/intersection-of-two-arrays-ii/1.题目解析
返回两个数组的交集 (结果中可以有重复元素)
2.算法分析
定义一个哈希表 unordered_map,遍历第一个数组,将 数组元素和出现的个数绑定扔进哈希表, 然后遍历第二个数组,元素在哈希表中出现,就插入到结果数组中,然后将该元素在哈希表中的个数--即可
3.算法代码
class Solution {
public:vector<int> intersect(vector<int>& nums1, vector<int>& nums2) {unordered_map<int, int> hash;for(auto& e : nums1)hash[e]++;vector<int> ret;for(auto& e : nums2){if(hash[e]){ret.push_back(e);hash[e]--;}}return ret;}
};
九、两句话中的不常见单词
884. 两句话中的不常见单词 - 力扣(LeetCode)https://leetcode.cn/problems/uncommon-words-from-two-sentences/description/
1.题目解析
返回两句话中互相在另一句话中没有出现的所有单词
2.算法分析
可以将两个字符串合在一起,提取出所有的单词同时扔进哈希表统计单词出现的次数,然后遍历一遍哈希表,出现次数为1的单词就是我们要的结果
3.算法代码
class Solution {
public:vector<string> uncommonFromSentences(string s1, string s2) {//1.将所有的单词提取出来vector<string> words;string tmp;string s = s1 + ' ' + s2;unordered_map<string, int> hash;for(size_t i = 0; i <= s.size(); i++){if(s[i] != ' ' && i != s.size())tmp += s[i];else{words.push_back(tmp);hash[tmp]++;tmp.clear();}}//2.从哈希表中提取结果vector<string> ret;for(auto [x, y] : hash)if(y == 1)ret.push_back(x);return ret;}
};
十、字符串中的第一个唯一字符
387. 字符串中的第一个唯一字符 - 力扣(LeetCode)https://leetcode.cn/problems/first-unique-character-in-a-string/
1.题目解析
找字符串中第一个只出现一次的字符
2.算法分析
数组模拟哈希表,遍历字符串s,统计出每个字符出现的次数,然后再遍历一遍哈希表,找出出现次数为1的字符,返回下标
3.算法代码
class Solution {
public:int firstUniqChar(string s) {int hash[26] = {0};for(auto& e : s)hash[e-'a']++;for(int i = 0; i < s.size(); i++)if(hash[s[i]-'a'] == 1)return i;return -1;}
};
相关文章:

【算法系列】哈希表
目录 哈希表总结 leetcode题目 一、两数之和 二、判定是否互为字符重排 三、存在重复元素 四、存在重复元素 II 五、字母异位词分组 六、在长度2N的数组中找出重复N次的元素 七、两个数组的交集 八、两个数组的交集 II 九、两句话中的不常见单词 哈希表总结 1.存储数…...

Git推送本地项目到gitee远程仓库
Git 是一个功能强大的分布式版本控制系统,它允许多人协作开发项目,同时有效管理代码的历史版本。开发者可以克隆一个公共仓库到本地,进行更改后将更新推送回服务器,或从服务器拉取他人更改,实现代码的同步和版本控制。…...

一键复制:基于vue实现的tab切换效果
需求:顶部栏有切换功能,内容区域随顶部切换而变化 目录 实现效果实现代码使用示例在线预览 实现效果 如下 实现代码 组件代码 MoTab.vue <template><div class"mo-tab"><divv-for"item in options"class"m…...

新手做抖音小店,卖什么最容易出单?抖音必爆类目来了!
哈喽!我是电商月月 新手做抖音小店没有经验,也不了解市场需求,最好奇的就是:卖什么商品最容易出单,还在犹豫的朋友可以看看这五种类目,在2024年下半年必定火爆一次 一.生活电器类 天气炎热&a…...
男人圣经 10
男人圣经 10 行业基因 你在对行业、客户群体、事情、核心优势上的高感知力 行业基因 你在对行业、客户群体、事情、核心优势上的高感知力 灵性,我感觉是对人、对事情、对行业的感知力,这就是你的天赋程度。 比如情圣,他比女人更懂自己&am…...
如何让路由器分配固定网段(网络号)ip
一.wan和lan wan广域网,负责连接互联网 lan局域网,负责保证一个区域内的设备可以互相通讯,比如wife就是让所有连接设备处于同一网段下 一.问题导入 1.我们平时在虚拟机和实体机通信时 必须让它们位于同一ip网段下。 通过winscp等软件进行…...

Q1保健品线上市场分析(三):牛初乳市场扩张,同比去年增长54%
近几年,牛初乳在多项科学研究支撑下,其卓越的“肠道免疫力”正得到越来越多的挖掘、验证和商业化尝试。因此,随着人们对健康饮食的重视,牛初乳产品的需求量也在逐年增加,市场潜力巨大。 根据鲸参谋数据显示࿰…...

使用docker-compose编排Lnmp(dockerfile) 完成Wordpress
目录 一、 Docker-Compose 1.1Docker-Compose介绍 1.2环境准备 1.2.1准备容器目录及相关文件 1.2.2关闭防火墙关闭防护 1.2.3下载centos:7镜像 1.3Docker-Compose 编排nginx 1.3.1切换工作目录 1.3.2编写 Dockerfile 文件 1.3.3修改nginx.conf配置文件 1.4Docker-Co…...

母婴店运用商城小程序店铺的效果是什么
母婴市场规模高,还可与不少行业无缝衔接,尤其是以90后、00后为主的年轻人,在备孕生育和婴儿护理前后等整体流程往往不惜重金且时间长,母婴用品无疑是必需品,商家需要多方面拓展全面的客户及打通场景随时消费路径。 运…...
大数据技术概述_2.大数据面临的5个方面的挑战
1. 大数据面临着5个主要问题 2012年冬季,来自IBM、微软、谷歌、HP、MIT、斯坦福、加州大学伯克利分校、UIUC等产业界和学术界的数据库领域专家通过在线的方式共同发布了一个关于大数据的白皮书。该白皮书首先指出大数据面临着5个主要问题,分别是异构性&a…...

《动手学深度学习(Pytorch版)》Task03:线性神经网络——4.29打卡
《动手学深度学习(Pytorch版)》Task03:线性神经网络 线性回归基本元素线性模型损失函数随机梯度下降 正态分布与平方损失 线性回归的从零开始实现读取数据集初始化模型参数定义模型定义损失函数定义优化算法训练 线性回归的简洁实现读取数据集…...
机器学习(二) ----------K近邻算法(KNN)+特征预处理+交叉验证网格搜索
目录 1 核心思想 1.1样本相似性 1.2欧氏距离(Euclidean Distance) 1.3其他距离 1.3.1 曼哈顿距离(Manhattan Distance) 1.3.2 切比雪夫距离(Chebyshev distance) 1.3.3 闵式距离(也称为闵…...
This error originates from a subprocess, and is likely not a problem with pip.
Preparing metadata (setup.py) ... errorerror: subprocess-exited-with-error python setup.py egg_info did not run successfully.│ exit code: 1╰─> [63 lines of output]WARNING: The repository located at mirrors.aliyun.com is not a trusted or secure host a…...

Python中关于子类约束的开发规范
Python中关于子类约束的开发规范 我们知道,在java和C#中有一种接口的类型,用来约束实现该接口的类,必须要定义接口中指定的方法 而在python中,我们可以基于父类子类异常来仿照着实现这个功能 class Base:def func():raise NotI…...

Isaac Sim 4 键盘控制小车前进方向(学习笔记5.8.2)
写的乱糟糟,主要是这两周忘了记录了...吭哧吭哧往下搞,突然想起来要留档,先大致写一个,后面再往里添加和修改吧,再不写就全忘了 有一个一直没解决的问题: 在保存文件时出现问题:isaac sim mism…...

「Python绘图」绘制太极图
python 绘制太极 一、预期结果 二、核心代码 import turtlepen turtle.Turtle()print("开始绘制太极")radius 100 pen.color("black", "black") pen.begin_fill() pen.circle(radius/2, 180) pen.circle(radius, 180) pen.left(180) pen.circ…...

解决html2canvas生成图片慢的问题
// 主要看那个点击事件就行 <divclass"textBox-right-board-group"v-for"item in screenList":key"item.id"><!-- 获取不同分辨率下的屏幕的展示的文字大小DPI: fontSize: getFontSize(item.resolutionRatio), --><di…...

模型智能体开发之metagpt-多智能体实践
参考: metagpt环境配置参考模型智能体开发之metagpt-单智能体实践 需求分析 之前有过单智能体的测试case,但是现实生活场景是很复杂的,所以单智能体远远不能满足我们的诉求,所以仍然还需要了解多智能体的实现。通过多个role对动…...

Java | Leetcode Java题解之第67题二进制求和
题目: 题解: class Solution {public String addBinary(String a, String b) {StringBuffer ans new StringBuffer();int n Math.max(a.length(), b.length()), carry 0;for (int i 0; i < n; i) {carry i < a.length() ? (a.charAt(a.leng…...
考过PMP之后,为什么建议学CSPM?
在项目管理领域,PMP证书和CSPM证书都是非常重要的认证,那么CSPM到底是什么?含金量如何?为什么建议学习CSPM?今天,我们一起来了解CSPM! CSPM是什么? CSPM中文全称:项目管理专业人员…...
浏览器访问 AWS ECS 上部署的 Docker 容器(监听 80 端口)
✅ 一、ECS 服务配置 Dockerfile 确保监听 80 端口 EXPOSE 80 CMD ["nginx", "-g", "daemon off;"]或 EXPOSE 80 CMD ["python3", "-m", "http.server", "80"]任务定义(Task Definition&…...
三维GIS开发cesium智慧地铁教程(5)Cesium相机控制
一、环境搭建 <script src"../cesium1.99/Build/Cesium/Cesium.js"></script> <link rel"stylesheet" href"../cesium1.99/Build/Cesium/Widgets/widgets.css"> 关键配置点: 路径验证:确保相对路径.…...
React Native在HarmonyOS 5.0阅读类应用开发中的实践
一、技术选型背景 随着HarmonyOS 5.0对Web兼容层的增强,React Native作为跨平台框架可通过重新编译ArkTS组件实现85%以上的代码复用率。阅读类应用具有UI复杂度低、数据流清晰的特点。 二、核心实现方案 1. 环境配置 (1)使用React Native…...

ESP32 I2S音频总线学习笔记(四): INMP441采集音频并实时播放
简介 前面两期文章我们介绍了I2S的读取和写入,一个是通过INMP441麦克风模块采集音频,一个是通过PCM5102A模块播放音频,那如果我们将两者结合起来,将麦克风采集到的音频通过PCM5102A播放,是不是就可以做一个扩音器了呢…...

P3 QT项目----记事本(3.8)
3.8 记事本项目总结 项目源码 1.main.cpp #include "widget.h" #include <QApplication> int main(int argc, char *argv[]) {QApplication a(argc, argv);Widget w;w.show();return a.exec(); } 2.widget.cpp #include "widget.h" #include &q…...

html-<abbr> 缩写或首字母缩略词
定义与作用 <abbr> 标签用于表示缩写或首字母缩略词,它可以帮助用户更好地理解缩写的含义,尤其是对于那些不熟悉该缩写的用户。 title 属性的内容提供了缩写的详细说明。当用户将鼠标悬停在缩写上时,会显示一个提示框。 示例&#x…...

【7色560页】职场可视化逻辑图高级数据分析PPT模版
7种色调职场工作汇报PPT,橙蓝、黑红、红蓝、蓝橙灰、浅蓝、浅绿、深蓝七种色调模版 【7色560页】职场可视化逻辑图高级数据分析PPT模版:职场可视化逻辑图分析PPT模版https://pan.quark.cn/s/78aeabbd92d1...

【JVM面试篇】高频八股汇总——类加载和类加载器
目录 1. 讲一下类加载过程? 2. Java创建对象的过程? 3. 对象的生命周期? 4. 类加载器有哪些? 5. 双亲委派模型的作用(好处)? 6. 讲一下类的加载和双亲委派原则? 7. 双亲委派模…...

华为OD机试-最短木板长度-二分法(A卷,100分)
此题是一个最大化最小值的典型例题, 因为搜索范围是有界的,上界最大木板长度补充的全部木料长度,下界最小木板长度; 即left0,right10^6; 我们可以设置一个候选值x(mid),将木板的长度全部都补充到x,如果成功…...

yaml读取写入常见错误 (‘cannot represent an object‘, 117)
错误一:yaml.representer.RepresenterError: (‘cannot represent an object’, 117) 出现这个问题一直没找到原因,后面把yaml.safe_dump直接替换成yaml.dump,确实能保存,但出现乱码: 放弃yaml.dump,又切…...