[LeetCode]题解(python):015-3Sum
题目来源:
https://leetcode.com/problems/3sum/
题意分析:
这道题目是输入一个数组nums。找出所有的3个数使得这3个数之和为0.要求1.输出的3个数按小到大排序,2.3个数的组合不重复。比如输入[-1,0,1,2,-1,-4],返回的应该是[[-1,0,1],[-1,-1,2]]。
题目思路:
如果直接暴力解决,那么时间复杂度是(O(n^3))。这样会TLE。
看到这道题目,我回想了leetcode的第一题。第一题是给出一个数组和一个target,找出数组的两个数使得这两个数等于target。在第一题中,我提到了”夹逼定理“。这里这个定理就可以用了。首先,我们将输入的数组nums排序。然后,从头开始取出一个数,nums[i],在nums[i+1:]中用夹逼定理找出num[j],nums[k](j<k)使得他们的和为0- nums[i]。然后将[nums[i],nums[j],nums[k]] append到答案数组。由于会存在多个组合使得nums[i] + nums[j] + nums[k] = 0,所以在比较的时候,如果nums[j] + nums[k] < 0- nums[i]时候,j += 1;如果nums[j] + nums[k] > 0 - nums[i]时候,k -= 1;如果nums[j] + nums[k] == 0 - nums[i]的时候,一直j += 1,k -= 1直到nums[j] != nums[j - 1]和nums[k] != nums[k + 1]。要注意的是,为了避免出现重复的组合,那么i + 的时候也要一直加到nums[i] != nums[i - 1]。
这种方法中,排序的时间复杂度是(O(n*log(n))),夹逼定理的时间复杂度是(O(n)),取数复杂度是(O(n)),总的时间复杂度是(O(n*log(n)) + O(n)*O(n)) = O(n^2)。所以时间复杂度是O(n^2)。
代码(python):
class Solution(object):
def threeSum(self, nums):
"""
:type nums: List[int]
:rtype: List[List[int]]
"""
size = len(nums)
ans = []
if size <= 2:
return ans
nums.sort()
i = 0
while i < size -2:
tmp = 0 - nums[i]
j = i + 1
k = size -1
while j < k:
if nums[j] + nums[k] < tmp:
j += 1
elif nums[j] + nums[k] > tmp:
k -= 1
else:
ans.append([nums[i],nums[j],nums[k]])
j += 1
k -= 1
while j < k:
if nums[j] != nums[j - 1]:
break
if nums[k] != nums[k + 1]:
break
j += 1
k -= 1
i += 1
while i < size - 2:
if nums[i] != nums[i - 1]:
break
i += 1
return ans
转载请注明出处:http://www.cnblogs.com/chruny/p/4820473.html
[LeetCode]题解(python):015-3Sum的更多相关文章
- 《LeetBook》leetcode题解(15):3Sum[M]
我现在在做一个叫<leetbook>的免费开源书项目,力求提供最易懂的中文思路,目前把解题思路都同步更新到gitbook上了,需要的同学可以去看看 书的地址:https://hk029.g ...
- [目录][Leetcode] Leetcode 题解索引
之前想边做题边写结题报告,发现有点力不从心,而且很多地方也是一知半解,现在重新做题,重新理解.这篇文章主要起一个目录的作用. 目前没有什么特定的顺序,基本都是看心情翻牌的,哈哈~ 我在Github上新 ...
- 【LeetCode题解】3_无重复字符的最长子串(Longest-Substring-Without-Repeating-Characters)
目录 描述 解法一:暴力枚举法(Time Limit Exceeded) 思路 Java 实现 Python 实现 复杂度分析 解法二:滑动窗口(双指针) 思路 Java 实现 Python 实现 复 ...
- 【LeetCode题解】225_用队列实现栈(Implement-Stack-using-Queues)
目录 描述 解法一:双队列,入快出慢 思路 入栈(push) 出栈(pop) 查看栈顶元素(peek) 是否为空(empty) Java 实现 Python 实现 解法二:双队列,入慢出快 思路 入栈 ...
- 【LeetCode题解】232_用栈实现队列(Implement-Queue-using-Stacks)
目录 描述 解法一:在一个栈中维持所有元素的出队顺序 思路 入队(push) 出队(pop) 查看队首(peek) 是否为空(empty) Java 实现 Python 实现 解法二:一个栈入,一个栈 ...
- 【LeetCode题解】844_比较含退格的字符串(Backspace-String-Compare)
目录 描述 解法一:字符串比较 思路 Java 实现 Python 实现 复杂度分析 解法二:双指针(推荐) 思路 Java 实现 Python 实现 复杂度分析 更多 LeetCode 题解笔记可以 ...
- 【LeetCode题解】25_k个一组翻转链表(Reverse-Nodes-in-k-Group)
目录 描述 解法一:迭代 思路 Java 实现 Python 实现 复杂度分析 解法二:递归(不满足空间复杂度) 思路 Java 实现 Python 实现 复杂度分析 更多 LeetCode 题解笔记 ...
- 【LeetCode题解】24_两两交换链表中的节点(Swap-Nodes-in-Pairs)
目录 描述 解法一:迭代 思路 Java 实现 Python 实现 复杂度分析 解法二:递归(不满足空间复杂度要求) 思路 Java 实现 Python 实现 复杂度分析 更多 LeetCode 题解 ...
- 【LeetCode题解】347_前K个高频元素(Top-K-Frequent-Elements)
目录 描述 解法一:排序算法(不满足时间复杂度要求) Java 实现 Python 实现 复杂度分析 解法二:最小堆 思路 Java 实现 Python 实现 复杂度分析 解法三:桶排序(bucket ...
- 【LeetCode题解】19_删除链表的倒数第N个节点(Remove-Nth-Node-From-End-of-List)
目录 描述 解法:双指针 思路 Java 实现 Python 实现 复杂度分析 更多 LeetCode 题解笔记可以访问我的 github. 描述 给定一个链表,删除链表的倒数第 n 个节点,并且返回 ...
随机推荐
- liunx 同步时间
ntpdate stdtime.gov.hk (美国) time.nist.gov (复旦)(国内用户推荐) ntp.fudan.edu.cn 微软公司授时主机(美国) time.windows.co ...
- A20 GPIO中断类型差别结果迥异的问题思考
A20GPIO中断类型差别结果迥异的问题思考 最近在使用全志A20做开发时,发现在处理中断的时候,用电平触发模式,报中断比较乱,用边沿触发则很稳定,不会乱报.笔者感到比较困惑,笔者用电平触发写的cod ...
- Android 怎样在linux kernel 中读写文件
前言 欢迎大家我分享和推荐好用的代码段~~ 声明 欢迎转载,但请保留文章原始出处: CSDN:http://www.csdn.net ...
- PID教程
PID教程 介绍 本教程将向您展示了比例每一个比例项 (P)的特点,积分项(I)和微分项 (D) 控制,以及怎样使用它们来获得所需的响应.在本教程中,我们会考虑下面单位反馈系统: Plant[被控对象 ...
- pkg-config的用法
pkg-config的用法 pkg-config pkg-config程序是干什么用的?简单的说就是向用户向程序提供相应库的路径.版本号等信息的程序. 譬如说我们运行以下命令:pkg-config ...
- Node.js笔记1
Node.js入门笔记 1. node -help 可以显示帮助信息2. node REPL 模式(Read-eval-print loop) 输入—求值—输出循环 直接在cmd输入node 可以进入 ...
- Add Two Numbers - C++链表操作
题目意思很简单,两个链表分别表示两个数,将两个数相加的结果存入一个新的链表中. 思路同样很简单:两个链表如果一样长,对应位置相加,如果某一个链表多了,则根据加的结果有无进位继续处理,全部结束后要考虑会 ...
- POJ 2689 Prime Distance(素数筛选)
题目链接:http://poj.org/problem?id=2689 题意:给出一个区间[L, R],找出区间内相连的,距离最近和距离最远的两个素数对.其中(1<=L<R<=2,1 ...
- USACO Section 5.4 TeleCowmunication(最小割)
挺裸的一道最小割.把每台电脑拆成一条容量为1的边,然后就跑最大流.从小到大枚举每台电脑,假如去掉后 最大流=之前最大流+1,那这台电脑就是answer之一了. -------------------- ...
- A Byte of Python 笔记(6)模块
第8章 模块 用户在程序中定义一次函数而重用代码,如果用户想在其他程序中重用很多函数,可以通过使用模块的方式. 模块就是一个包含了所有用户定义的函数和变量的文件.为了在其他程序中重用模块,模块的文件名 ...