LeetCode 第15题-三数之和

1. 题目

2.题目分析与思路

3.思路

1. 题目

给定一个包含 n 个整数的数组 nums,判断 nums 中是否存在三个元素 a,b,c ,使得 a + b + c = 0 ?找出所有满足条件且不重复的三元组。

注意:答案中不可以包含重复的三元组。

例如, 给定数组 nums = [-1, 0, 1, 2, -1, -4],

满足要求的三元组集合为:
[
[-1, 0, 1],
[-1, -1, 2]
]

2. 思路

  这道题最直接想到的应该是两数之和,两数之和还是比较基础的,采用通知记录的方式,维护一个字典,看新的数是否属于这个字典的键即可。三数之和也可以使用类似的办法,但是题目要求的是不能有重复的,这就比较难办了,那可能只有先将其排序,然后判断一下他们是否在集合中,思路就显而意见了,代码如下:

def threeSum(self, nums: List[int]) -> List[List[int]]:
        result = []
        for i,j in enumerate(nums):
            temp = nums[:i]+nums[i+1:]
            dic1 = {}
            dic2 = {}
            for count,k in enumerate(temp):
                if k not in dic1:
                    dic1[-j-k] = k
                else:
                    dic2[tuple(sorted([j,k,-j-k]))] = [j,k,-j-k]
        return dic2.values()

3. 改进

    然而不幸的是,这个复杂度太高,跑不过所有case便会超时,在这之前我使用的是判断list是否在list中,这样的话更没有办法通过所有的case,复杂度太高,优化以后使用字典但还是在全是0的case失败了。

    经过修改后和一些边界条件,给出一个通过了case,但是极其慢的解法,我称其为无情解法:

def threeSum(self, nums: List[int]) -> List[List[int]]:
        dic2 = {}
        if (len(set(nums) ) == 1)and (len(nums) > 2): #主要是去除全是0 的情况,全是0 就会导致最后的循环复杂度过高
            if 0 in set(nums):
                return [[0,0,0]]
        for i,j in enumerate(nums):
            temp = nums[:i]+nums[i+1:]
            dic1 = {}
            for count,k in enumerate(temp):
                if k not in dic1:
                    dic1[-j-k] = k
                else:
                    dic2[tuple(sorted([j,k,-j-k]))] = [j,k,-j-k]
        return dic2.values()

   下面给出正确的解法,使用双指针

class Solution:
    def threeSum(self, nums: List[int]) -> List[List[int]]:
        nums = sorted(nums)
        res = []
        dic1 = {}
        for i,j in enumerate(nums):
            if j > 0:
                continue
            temp = nums[i+1:]
            left = 0
            right = len(temp)-1
            while(left < right):
                
                if j + temp[left]+temp[right] == 0:
                    dic1[(j,temp[left],temp[right])] = [j,temp[left],temp[right]]
                    # res.append([j,temp[left],temp[right]])
                    right -= 1
                elif j + temp[left]+temp[right] > 0:
                    right -= 1
                else:
                    left += 1
        return dic1.values()

猜你喜欢

转载自www.cnblogs.com/tjpeng/p/11621435.html