Leetcode力扣 1 | 两数之和 Two Sum —— python

Leetcode力扣 1 | 两数之和 Two Sum

该系列以提高编程能力、学习数据结构与算法为目的

  • 编程语言:python

Question


给定一个数组nums、一个目标target值(以下简写成nums、target)

我们的目的是在nums中,找到两个元素,使其相加等于target值,然后返回这两个元素在nums中的索引,就是数组下标。

题目中给了三个示例:

  1. 第一个返回下标0和1,因为2与7的和为9
  2. 第二个返回下标1和2,因为2与4的和为6
  3. 第三个返回下标3和3,因为3与3的和为6

前面两个例子比较好理解。第三个 由于有相同的元素, 所以在编程的时候可能返回同一个索引,题目要求是同一个元素不能重复出现。所以示例3如果返回0,0则不符合要求。

这是特殊的情况,需要考虑到。

我一开始也没注意这个点。所以接下来看解答的时候如何避免返回相同元素。

Answer

Brute Force 暴力求解法


我们将第一个示例修改一下顺序进行讲解:

  1. 首先我们要找到两个数的和为9
  2. 考虑先从数组的nums[0]开始,
  3. 然后依次遍历nums[0]+nums[i], i = 1, 2, 3……
    这里的i从1开始,也就是0的下一位开始可以避免我们前面所说的元素重复问题
  4. 判断语句就是if num[0] + num[i] == target
  5. 如果等于 我们就返回数组下标 return 0, i
  6. 遍历了0和剩余项的和没有找到目标元素的话
  7. 继续从nums[1]开始,“往后”遍历。
    同样为了避免重复问题,下一层for循环的元素从nums[2]开始
  8. 重复上面的步骤,最后可以返回数组

最后这题返回的是[2, 3]

下面是具体代码

  • 暴力求解的时间复杂度是O(n²)
  • 暴力求解的空间复杂度是O(1)

暴力求解的时间复杂度是很糟糕的,很多题都可以用暴力求解,但我们一般不用,这是作为最后的选择一般。

HashTable 哈希表法

python的字典与哈希表都是应用映射结构

哈希表在不出现“冲突”,
也就是一个key对应一个value的时候搜索的时间复杂度是O(1)

我们考虑用哈希表 我也是重新学习了一下哈希表的知识才做这题的
所以如果没有知识储备的同学 要再去理解一下哈希表再看

题目给定nums和target

首先我们把数组转换成哈希表(字典)

        HashTable = {}  #创建一个空字典
        for i in range(len(nums)):
            HashTable[nums[i]] = i

然后与暴力法类似。

  1. 遍历数组 diff = target - nums[ j ] (diff是difference的意思,就是提醒下标不同)
  2. 然后我们要在哈希表中找到是否存在key值等于diff的
        for j in range(len(nums)):
            diff = target - nums[j]
            if (diff in HashTable) and (HashTable[diff] != j):
               return [j, HashTable[diff]]
  1. 判断句来检测是否有这样一个key
    除了判断是否存在 还需要检查这个key的value值是否是元素本身

比如题目给出的示例第三个
[3, 3] 如果按照上述哈希查找的方法 我们会找到相同的元素并返回下标
很明显这是不满足要求的

  1. 所以我们要在判断语句那里加上另一个判断
	if (diff in HashTable) and (HashTable[diff] != j):
  • 哈希方法的时间复杂度最大为O(n),这个n是在创建哈希表的时候执行的
  • 在哈希表中查找给定key的value的值时间复杂度是O(1)。
  • 哈希方法在发生“冲突”的时候时间复杂度降到O(n)
  • 这题的Hash表key值会覆盖 这个bug暂时还不会改 但是LeetCode可以通过滴
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值