15. 3Sum、16. 3Sum Closest和18. 4Sum
15 3sum
Given an array nums
of n integers, are there elements a, b, c in nums
such that a + b + c = 0? Find all unique triplets in the array which gives the sum of zero.
Note:
The solution set must not contain duplicate triplets.
Example:
- Given array nums = [-1, 0, 1, 2, -1, -4],
- A solution set is:
- [
- [-1, 0, 1],
- [-1, -1, 2]
- ]
思考:1、想了很久,不知道怎么做。只能想到时间复杂度比较高的做法。在网上查到,这个3sum问题是比较经典的,其解法基于2sum。2sum问题是给定一个排好序的数组,问有哪些两个元素相加为
0。解法是一个下标指向第一个,另一个下标指向最后一个。
有如下结论及其规则:
一、如果num[1]+num[n]>0,那么2和n的和大于0,3和n的和也会大于0。等等。所以就没必要再去计算以最后一个为右边界的组合。考虑1,..,n-1这个范围内的组合,即移动后一个。
二、如果num[1]+num[n]<0,那么1和n-1的和,1和n-2的和也会小于0。等等。所以就没必要去计算以1为左边界的组合。考虑2,...,n这个范围内的组合,即移动前一个下标。
不断进行这个操作,最终遍历所有可能的组合,而不是每个组合。- 3sum问题可以分解成2sum。取出数组第一个元素X,在剩下的数组里找到两数之和为-X,这就是2sum问题。
- 由于c语言不支持动态添加元素,所以用c++可能更方便一些,故实现如下。ps:用c语言做了一下,一直free内存那里出问题。
- class Solution {
- public:
- vector<vector<int>> threeSum(vector<int>& nums) {
- vector<vector<int> > ans;
- int index1,index2;
- if(nums.size()<) return ans;
- sort(nums.begin(), nums.end());
- for (int i = ; i <= nums.size()-; i++) {
- if(i!= && nums[i-]==nums[i]) continue;
- index1 = i+;
- index2 = nums.size()-;
- /*if(i==0) {
- index1 = 1;
- index2 = nums.size()-1;
- }
- else if (i== nums.size()-1) {
- index1 = 0;
- index2 = nums.size()-2;
- }else {
- index1 = 0;
- index2 = nums.size()-1;
- }*/
- while(index1<index2) {
- if(nums[i]+nums[index1]+nums[index2]==) {
- int sol[] = { nums[i], nums[index1], nums[index2] };
- ans.push_back(vector<int> (sol, sol + ));
- //printf("i is %d.index1 is %d.index2 is %d.\n", i,index1,index2);
- index1++;while(nums[index1]==nums[index1-]) index1++;
- index2--;while(nums[index2]==nums[index2+]) index2--;
- }else if (nums[i]+nums[index1]+nums[index2]>) {
- index2--;
- }else {
- index1++;
- }
- }
- }
- return ans;
- }
- };
16 3sum closet
Given an array nums
of n integers and an integer target
, find three integers in nums
such that the sum is closest to target
. Return the sum of the three integers. You may assume that each input would have exactly one solution.
Example:
- Given array nums = [-1, 2, 1, -4], and target = 1.
- The sum that is closest to the target is 2. (-1 + 2 + 1 = 2).
和上面是简单变形关系,所用的原理一样。因为此次并不需要返回数组的数组,所以又用c语言来表示我的行为。
- void my_qsort(int *nums, int index1, int index2) {
- if(index1==index2) return;
- int pre,last;
- int tmp;
- pre = index1;
- for(last=index1+; last<=index2; last++) {
- if(nums[last]<nums[index1]) {
- pre++;
- tmp = nums[pre];
- nums[pre] = nums[last];
- nums[last] = tmp;
- }
- }
- tmp = nums[index1];
- nums[index1] = nums[pre];
- nums[pre] = tmp;
- if(pre==index1) {
- my_qsort(nums, index1+, index2);
- }else if(pre==index2) {
- my_qsort(nums, index1, index2-);
- }else {
- my_qsort(nums, index1, pre-);
- my_qsort(nums, pre+, index2);
- }
- }
- int threeSumClosest(int* nums, int numsSize, int target) {
- int ret,index1,index2,tmp;
- my_qsort(nums, , numsSize-);
- for(int i = ; i<numsSize; i++)
- printf("%d ", nums[i]);
- printf("\n");
- ret = nums[] + nums[] + nums[];
- for(int i=; i<=numsSize-;i++) {
- index1 = i+;
- index2 = numsSize-;
- while(index1<index2) {
- tmp = nums[i] + nums[index1] + nums[index2];
- if(tmp == target) return tmp;
- if(abs(tmp-target)<abs(ret-target)) ret = tmp;
- if(tmp>target) {
- index2--;
- }else if(tmp < target) {
- index1++;
- }
- }
- }
- return ret;
- }
18. 4Sum
Given an array nums
of n integers and an integer target
, are there elements a, b, c, and d in nums
such that a + b + c + d = target
? Find all unique quadruplets in the array which gives the sum of target
.
Note:
The solution set must not contain duplicate quadruplets.
Example:
- Given array nums = [1, 0, -1, 0, -2, 2], and target = 0.
- A solution set is:
- [
- [-1, 0, 0, 1],
- [-2, -1, 1, 2],
- [-2, 0, 0, 2]
- ]
思考:首先按一定顺序取前两个数,共有(n-3)*(n-2)个组合,对于剩下的两个数就用首尾指针进行移动检查。
这里我有一个小小的优化。看下line 12行的代码,如果nums[i]大于0,nums[i]>terget,那么后面的三个数一定大于0。既然后面的三个数都大于0,nums[i]加上大于的0
一定大于target。所以就没有必要再继续检查。第15行代码同理。
- class Solution {
- public:
- vector<vector<int>> fourSum(vector<int>& nums, int target) {
- vector<vector<int>> ans;
- sort(nums.begin(), nums.end());
- int len = nums.size();
- int i,j,k,l;
- for(i=; i<=len-; i++) {
- if(nums[i]>target && nums[i]>=) continue;
- if(i>= && nums[i]==nums[i-]) continue;
- for(j=i+; j<=len-; j++) {
- if(nums[i]+nums[j]>target && nums[j]>=) continue;
- if(j>=i+ && nums[j]==nums[j-]) continue;
- k = j + ;
- l = len - ;
- while(k<l) {
- if(nums[i]+nums[j]+nums[k]+nums[l]>target) {
- l--;
- }else if(nums[i]+nums[j]+nums[k]+nums[l]<target){
- k++;
- }else {
- int sol[] = { nums[i], nums[j], nums[k],nums[l] };
- ans.push_back(vector<int> (sol, sol + ));
- k++;
- while(nums[k]==nums[k-]) k++;
- l--;
- while(nums[l]==nums[l+]) l--;
- }
- }
- }
- }
- return ans;
- }
- };
15. 3Sum、16. 3Sum Closest和18. 4Sum的更多相关文章
- leetcode 1.Two Sum 、167. Two Sum II - Input array is sorted 、15. 3Sum 、16. 3Sum Closest 、 18. 4Sum 、653. Two Sum IV - Input is a BST
1.two sum 用hash来存储数值和对应的位置索引,通过target-当前值来获得需要的值,然后再hash中寻找 错误代码1: Input:[3,2,4]6Output:[0,0]Expecte ...
- LeetCode 15. 3Sum 16. 3Sum Closest 18. 4Sum
n数求和,固定n-2个数,最后两个数在连续区间内一左一右根据当前求和与目标值比较移动,如果sum<target,移动较小数,否则,移动较大数 重复数处理: 使i为左至右第一个不重复数:while ...
- 【LeetCode】18. 4Sum 四数之和
作者: 负雪明烛 id: fuxuemingzhu 个人博客:http://fuxuemingzhu.cn/ 个人公众号:负雪明烛 本文关键词:four sum, 4sum, 四数之和,题解,leet ...
- 1. Two Sum&&15. 3Sum&&18. 4Sum
题目: 1. Two Sum Given an array of integers, return indices of the two numbers such that they add up t ...
- [LeetCode][Python]16: 3Sum Closest
# -*- coding: utf8 -*-'''__author__ = 'dabay.wang@gmail.com' 16: 3Sum Closesthttps://oj.leetcode.com ...
- 《LeetBook》leetcode题解(16):3Sum Closest [M]
我现在在做一个叫<leetbook>的免费开源书项目,力求提供最易懂的中文思路,目前把解题思路都同步更新到gitbook上了,需要的同学可以去看看 书的地址:https://hk029.g ...
- LeetCode 16. 3Sum Closest(最接近的三数之和)
LeetCode 16. 3Sum Closest(最接近的三数之和)
- [LeetCode] 16. 3Sum Closest 最近三数之和
Given an array nums of n integers and an integer target, find three integers in nums such that the s ...
- Leetcode 16. 3Sum Closest(指针搜索)
16. 3Sum Closest Medium 131696FavoriteShare Given an array nums of n integers and an integer target, ...
随机推荐
- Apache httpd.conf配置文件 2(Main server configuration)
### Section 2: 'Main' server configuration # # The directives in this section set up the values used ...
- light oj1028 - Trailing Zeroes (I)
1028 - Trailing Zeroes (I) We know what a base of a number is and what the properties are. For exa ...
- Unity5.5.6 升级到 2018.4.1 打包出现的问题 : Gradle version 2.10 is required. Current version is 5.1.1
起因:最近要在googleplay上架新游戏,而谷歌要求新上架的应用要支持64位,鉴于老版本的unity不支持打包64位apk,所以决定升级unity版本到2018.4.1, 但打包过程中出现了几个问 ...
- css沉默
css变色龙实现. ==== css 1 水平居中和垂直居中. 2 css布局方式. 3 你写过UI框架么.
- Arm开发板+Qt学习之路
从2015.11.13日开始接触arm开发板,开始学习Qt,到现在已经四个月零17天了,从一个拿到开发板一无所知的小白,到现在能够在开发板上进行开发,有付出有收获. 之前一直没有时间将这个过程中的一些 ...
- 【Android开发艺术探索】四大组件的工作过程
个人博客 http://www.milovetingting.cn 四大组件的工作过程 四大组件:Activity.Service.BroadcastReceiver.ContentProvider ...
- 最短路问题 Dijkstra算法- 路径还原
// 路径还原 // 求最短路,并输出最短路径 // 在单源最短路问题中我们很容易想到,既然有许多条最短路径,那将之都存储下来即可 // 但再想一下,我们是否要把所有的最短路径都求出来呢? // 实际 ...
- springBoot进阶02
SpringBoot进阶02 1. 日志的使用 1.1 基本使用 /** * 获取日志记录器 */ Logger logger = LoggerFactory.getLogger(this.getCl ...
- 安装Linux系统时LSI RAID卡的驱动挂载
转载原文地址:https://www.jianshu.com/p/64415712401e 当使用较新的SAS卡来安装Linux系统时,经常会遇到在系统安装界面读不到RAID的情况,这时就需要考虑Li ...
- 在香蕉派的树莓派系统上配置 Syncthing 自启动
在香蕉派的树莓派系统上配置 Syncthing 自启动 —— 魏刘宏 2020 年 1 月 19 日 首先做个名词解释,” 香蕉派” 是国内一款山寨树莓派的硬件产品,” 树莓派系统” 指的是”rasp ...