两数之和 C++实现(力扣题目1)

news2025/1/18 18:55:55

给定一个整数数组 nums 和一个整数目标值 target,请你在该数组中找出和为目标值 target 的那两个整数,并返回它们的数组下标。

你可以假设每种输入只会对应一个答案。但是,数组中同一个元素在答案里不能重复出现。

你可以按任意顺序返回答案。

示例 1:

输入:nums = [2,7,11,15], target = 9
输出:[0,1]
解释:因为 nums[0] + nums[1] == 9 ,返回 [0, 1] 。
示例 2:

输入:nums = [3,2,4], target = 6
输出:[1,2]
示例 3:

输入:nums = [3,3], target = 6
输出:[0,1]

  • 思路一

看到这道题目的第一想法依然是暴力法,想要在数组中找到和为目标值target的那两个数,那我把整个数组都遍历一遍,两两相加,看它们的和是否为target,如果不是的话我再换两个数,如此进行下去,就一定会找到我们需要的数以及它们对应的下标。

 

暴力法的流程思想就是上面这样的,两两相加看它们的和是否等于target,但是我们可以仔细看一看,这样其实是有重复运算的,比如【第一轮的①和第二轮的①】运算结果是一样的,两者对最后我们要求解的结果的影响是一样的,无非返回结果是[0,1],[1,0]顺序不同而已。所以在实际编程时应该优化一下(在程序中优化方法就是 j=i+1)

class Solution{
public: 
        vector<int> twoSum(vector<int>&nums,int target){
            int i,j;
            for(i=0;i<nums.size();i++)
            {
                for(j=i+1;j<nums.size();j++)
                {
                    if(nums[i]+nums[j]==target;
                    return {i,j};
                }
            }
            return {i,j};
    }
};

这个程序应该比较容易理解,就不逐句给大家讲解了。 

  •  思路二

        利用哈希表。刚才上面我们使用的两层for循环遍历的方法可以解决这个问题,而且相信大家拿到这道题的第一想法都是思路一,但是呢这种方法用了两层for循环,所以时间复杂度比较高。为了简化时间复杂度就尝试转换一下思路,用哈希表。

        我们先看解题思路是怎样的

 

对应的程序如下: 

class Solution {
public:
    vector<int> twoSum(vector<int>& nums, int target) {
        unordered_map<int,int> mm;           //key是元素值,val是下标
        for(int i=0;i<nums.size();i++)
        {
            int find=target-nums[i];
            if(mm.count(find)!=0)
            {
                vector<int> vec{i,mm[find]};  //mm[find] 是 如果存在该变量则直接返回对应value,
                                              //如果不存在则增加该key值并自动初始化为0(这时候一定是存在的)
                return vec;
            }                 
            //unordered_map<int,int>
            mm[nums[i]]=i;                    // map的初始化方法之 直接赋值
        }
        return {};
    }
};

下面对这个程序进行简单注释: 

unordered_map<int,int> mm;           //key是元素值,val是下标

这一句就是创建了一个容器mm,unordered_map类型,其中的key是int类型,value也是int类型 。可能大家对这一句话完全不理解,unordered_map类型是什么类型?它里面为什么可以同时存两种类型的元素?key是什么?value又是什么?一头雾水完全不懂,不要着急下面为大家逐一解答:

首先unordered_map类型是C++STL标准库中提供的一种存储数据的结构(或者叫容器),前缀unordered就是“无序地”意思。与它看起来有点像的还有(map、multimap、unordered_map,大家感兴趣的可以去查一下)

为了方便起见我们先看不带前缀的map,map是STL的一个关联容器,关联式容器依据特定的排序准则,自动为其元素排序。map的元素都是“实值/键值”所形成的一个队组(key/value pairs),每个元素有一个键,是排序准则的基础,每个键只能出现一次不能重复。

而加上前缀unordered后成为unordered_map,就表示把元素添加进去后,不会根据键值进行自动排序,其中的元素顺序就是你添加元素的顺序。

 for(int i=0;i<nums.size();i++)

这一句就是逐个遍历数组中的元素

int find=target-nums[i];

定义一个变量find,这个find的作用就是我们之前提到的 每当遍历到一个元素 i ,就去哈希表里查找有没有一个元素等于target – i  (注意表述与代码稍有不一)

if(mm.count(find)!=0)
            {
                vector<int> vec{i,mm[find]};  //mm[find] 是 如果存在该变量则直接返回对应value,
                                              //如果不存在则增加该key值并自动初始化为0(这时候一定是存在的)
                return vec;

count()是 C++中unordered_map的内置方法,用于通过给定 key 对unordered_map中存在的元素数量进行计数。如果count(find)不为0,就意味着在unordered_map中找到了我们需要的数字,此时返回vec{i,mm[find]}就可以了

mm[nums[i]]=i;                    // map的初始化方法之 直接赋值

这是unordered_map的一种初始化方法,当然也有其他初始化方法,这里不做详细介绍,请大家自行查询一下。

 

 到这里我们已经成功地利用两种方法解决这道题目了,但是我们应该思考一下:

  1. 为什么第二种方法(哈希表)的存取查找比较快?

        (方法一运行时长)

         (方法二运行时长)

 

 因为有种算法叫哈希算法,哈希算法会根据你要存入的数据,先通过该算法计算出一个地址值,这个地址值就是你需要存入到集合当中的数据的位置,而不会像数组那样一个个地进行挨个存储,挨个遍历一遍后面有空位就存这种情况。当你查找时,也是根据这个哈希算法来的,将你要查找的数据进行计算,得出一个地址,这个地址会映射到集合当中的位置,这样就能直接去这个位置找了,而不需要像数组那样,一个一个去遍历比对查找。这样自然就提高了速度。

(这么说可能大家还是不懂)再介绍一下,哈希算法有一个强大的功能,它使得我们通过查找关键字但不需要逐个比较的方法就可以获得需要的记录的存储位置。存储位置=y(关键字),这个y就是哈希算法。它使得每个关键字key对应一个存储位置,查找时根据这个确定的对应关系找到给定值key的映射y(key),若查找集合中存在这个记录,则必定在y(key)的位置上。

整个过程就两步:①在存储时,通过y函数计算一个地址,并按照这个地址存储该记录②当查找记录时,我们通过同样的y函数计算记录的地址,按此地址访问该记录。由于存取过程采用的是同一个y函数,因此结果当然也是相同的

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

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

相关文章

SQL案例-高校信息管理系统实现要求

SQL案例-高校信息管理系统实现要求 (1) 建表 stuInfo(学生信息表) 字段名称数据类型说明stuName字符学生姓名&#xff0c;该列必填&#xff0c;要考虑姓氏可能是两个字的&#xff0c;如欧阳俊雄stuNo字符学号&#xff0c;该列必填&#xff0c;学号不能重复&#xff0c;且必须…

AC规则-4-规则和冲突解决

3.3 Introduction to Access Control Rule Conflict Resolution 3.3 访问控制规则冲突解决简介 本节从高层次讨论访问控制规则冲突解决。 本文档稍后会提供更多详细信息。 规则的优先级不是基于它在其他规则中的阅读顺序。 管理冲突规则的策略基于三个基本原则&#xff08;…

linux中 list_entry 设计背景及原理解析

Linux 2.4.22 在这一版本中的 list_entry的宏定义实现如下&#xff1a; #define list_entry(ptr, type, member) \((type *)((char *)(ptr)-(unsigned long)(&((type *)0)->member)))乍一看&#xff0c;会觉得特别复杂&#xff0c;其实分析之后&#xff0c;会发现清晰…

LeetCode高频算法刷题记录8

文章目录 1. 零钱兑换【中等】1.1 题目描述1.2 解题思路1.3 代码实现 2. 最小栈【最小栈】2.1 题目描述2.2 解题思路2.3 代码实现 3. 最长有效括号【困难】3.1 题目描述3.2 解题思路3.3 代码实现 4. 从前序与中序遍历序列构造二叉树【中等】4.1 题目描述4.2 解题思路4.3 代码实…

day8 域名解析与http服务器实现原理

域名解析gethostbyname函数 主机结构在 <netdb.h> 中定义如下 结构的成员包括&#xff1a; h_name &#xff1a;主机的正式名称 h_aliases&#xff1a;主机的备用名称数组&#xff0c;以 NULL 结尾指针 h_addrtype&#xff1a;地址类型;&#xff08;AF_INET或AF_INET…

基础知识6

知乎上的面试题&#xff1a;https://zhuanlan.zhihu.com/p/546032003 一、Topk问题以及变种&#xff0c;各种解法 微博的热门排行就属于 TopK 问题 TopK 一般是要求在 N 个数的集合中找到最小或者最大的 K 个值&#xff0c;通常 N 都非常得大。 算法的优点是不用在内存中读入全…

经典组件知识(kafka,ngix)

消息队列的作用 解耦、削峰、 异步&#xff08;非必要逻辑异步运行&#xff0c;加快响应速度&#xff09; kafka 首先有个topic的概念&#xff0c;类似于表。 Partition 分区&#xff1a;一个topic下面有多个分区&#xff0c;这些分区会存储到不同的服务器上面&#xff0c;或者…

如何使用 Django 进行测试驱动开发,我来告诉你

所谓测试驱动开发(TDD)&#xff0c;就是先编写测试用例&#xff0c;然后编写代码来满足测试用例&#xff0c;具体包含以下步骤&#xff1a; 编写测试用例。编写代码满足测试用例中的需求。运行测试用例。如果通过&#xff0c;说明代码满足了测试用例所定义的需求。如果未通过&…

armday2

.text .global _start _start: bl LED1_INITbl LED1_ONbl delay_1sbl LED1_OFFbl LED2_INITbl LED2_ONbl delay_1sbl LED2_OFFbl LED3_INITbl LED3_ONbl delay_1sbl LED3_OFFbl _start/**********LED1点灯PE10**************/ LED1_INIT:1.通过RCC_HB4_ENSETR寄存器设置GPIOE组…

PoseiSwap:为何青睐 Layer3?又为何选择 Celestia 作为技术伙伴?

自 PoseiSwap 在 Nautilus Chain 上线后&#xff0c;该 DEX 的整体市场进展十分顺利。我们看到&#xff0c;其不仅在 4 月&#xff0c;以 1000万美元的估值&#xff0c; 获得了来自于 Zebec Labs 的首轮 150 万美元的融资。而在本月&#xff0c;在 Zebec 生态的帮助下&#xff…

利用prusa 3d打印地形模型 如何合理切片并提高打印速度

如上图&#xff0c;我们选择打印一个宽10cm 的地形模型&#xff0c;通过prusa切片&#xff0c;显示时间为22小时31分钟。这个速度大概一天&#xff0c;确实不是我们要的速度&#xff0c;如何提高速度又不失去打印细节且不增加失败风险呢。 1.减少填充 10%的填充对于创想三维en…

RK3568平台开发系列讲解(驱动基础篇)RK平台UART的使用

🚀返回专栏总目录 文章目录 一、引脚定义1.1 UART91.2 RS232和RS485二、设备树配置三、调试3.1 连接硬件3.2 打开主机的串口终端3.3 板子发送数据3.4 板子接收数据3.5 主机退出kermit串口连接四、UART2普通串口配置沉淀、分享、成长,让自己和他人都能有所收获!😄 📢本篇…

C++——模板初阶

文章目录 一.泛型编程二.函数模板1.函数模板的概念2.函数模板的格式3.函数模板的原理4.函数模板的实例化&#xff08;1&#xff09;隐式实例化&#xff08;2&#xff09;显式实例化 5.模板参数的匹配原 三.类模板1.类模板的定义格式2.类模板的实例化 前言&#xff1a; 本章我们…

Flutter问题记录 - Text组件设置不限行数无效

文章目录 前言开发环境问题描述问题分析解决方案最后 前言 梳理Flutter项目的过程中发现还有一些遗留的TODO没处理&#xff0c;其中有一个和Text组件相关。 开发环境 Flutter: 3.7.12Dart: 2.19.6 问题描述 Text组件设置maxLines: null不限制行数&#xff1a; Text(The […

gradio入门示例

随着chat-gpt等机器人对话框架的流行&#xff0c;让一个名为gradio的框架也火热起来&#xff0c;这个框架可以开启一个http服务&#xff0c;并且带输入输出界面&#xff0c;可以让对话类的人工智能项目快速运行。 gradio号称可以快速部署ai可视化项目。 下面通过两个示例来感受…

C++学习记录——이십사 位图、布隆过滤器、哈希切割

文章目录 1、位图位图应用优缺点 2、布隆过滤器1、哈希函数2、删除 3、哈希切割应用 本篇gitee 1、位图 先看一个题目&#xff1a; 给40亿个不重复的无符号整数&#xff0c;没排过序。给一个无符号整数&#xff0c;如何快速判断一个树是否在这40亿个数中&#xff1f; 这里可能…

《面试1v1》线程池

我是 javapub&#xff0c;一名 Markdown 程序员从&#x1f468;‍&#x1f4bb;&#xff0c;八股文种子选手。 面试官&#xff1a; 你好&#xff0c;很高兴见到你。请问你对线程池有什么了解&#xff1f; 候选人&#xff1a; 你好&#xff0c;我对线程池非常了解。线程池是一种…

前后端联调统一校验规则

文章目录 统一校验实现1.什么是统一校验2.统一校验的实现&#xff08;1&#xff09;引入依赖&#xff08;2&#xff09;基于注解&#xff08;3&#xff09;使用案例【1】定义校验规则【2】开启校验【3】统一异常处理器捕获校验产生的异常 3.分组校验(1)定义公共的校验分组(2)定…

完全自主研发,聚芯微发布3D dToF图像传感器芯片!

日前&#xff0c;由中国半导体行业协会IC设计分会&#xff08;ICCAD&#xff09;、芯原股份、松山湖管委会主办的主题为“AR/VR/XR元宇宙”的“2023松山湖中国IC创新高峰论坛”正式在广东东莞松山湖召开。武汉市聚芯微电子有限责任公司发布了完全自主知识产权的3D dToF图像传感…

Spring面试整理

什么是Spring&#xff1f; Spring的优缺点&#xff1f; Spring的模块组成 Spring框架中使用了哪些设计模式&#xff1f; 详细讲解下核心容器&#xff08;Spring context&#xff09;模块 Spring框架中有哪些不同类型的组件 Spring控制反转&#xff08;IOC&#xff09; 什…