15题
补充vector 创建数组
vector<int> res;//定义一维数组
vector<vector<int>>res//定义二维数组
vector<int>(int n)//创建一个vector,元素个数为n
vector<int>(int n,const t)//创建一个vector,元素个数为n,且值均为t
vector(const vector&)//拷贝构造函数
push_back()在Vector最后添加一个元素(参数为要插入的值)
pop_back() //移除最后一个元素
clear() //清空所有元素
empty() //判断vector是否为空,如果返回true为空
erase() // 删除指定元素
sort(nums.begin(),nums.end()) //排序
思路步骤:(排序+双指针)
1.创建一个二维数组 vector<vector<int>> res;
2.获取数组的长度 如果小于3则返回
3.对数组进行排序 sort()(从小到大)
4.for循环
- 判断第一个数是否大于0
- 去重第一步:判断 i 与 i+1是否相等 j=i+1 h=length-1
- 计算sum=nums[ i ]+nums[ j ]+nums[ h ] (前提 j < h)
- 判断sum=0?res.push_back()
- 去重第二部:判断 j+1与 j 是否相等 j++ 判断 h+1 与 h 是否相等 h--
5.判断sum>0? h--
6.判断sum<0? j++
7.返回res
主要是去重!
class Solution {
public:
vector<vector<int>> threeSum(vector<int>& nums) {
//定义一个结果集
vector<vector<int>> res;
//数组的长度
int len = nums.size();
//当前数组的长度为空,或者长度小于3时,直接退出
if( len <3){
return res;
}
//将数组进行排序
sort(nums.begin(),nums.end());
//遍历数组中的每一个元素
for(int i = 0; i<len;i++){
//如果遍历的起始元素大于0,就直接退出
//原因,此时数组为有序的数组,最小的数都大于0了,三数之和肯定大于0
if(nums[i]>0){
break;
}
//去重,当起始的值等于前一个元素,那么得到的结果将会和前一次相同
if(i > 0 && nums[i] == nums[i-1]) continue;
int l = i +1;
int r = len-1;
//当 l 不等于 r时就继续遍历
while(l<r){
//将三数进行相加
int sum = nums[i] + nums[l] + nums[r];
//如果等于0,将结果对应的索引位置的值加入结果集中
if(sum==0){
// 将三数的结果集加入到结果集中
res.push_back(vector<int>{nums[i], nums[l], nums[r]});
//在将左指针和右指针移动的时候,先对左右指针的值,进行判断
//如果重复,直接跳过。
//去重,因为 i 不变,当此时 l取的数的值与前一个数相同,所以不用在计算,直接跳
while(l < r && nums[l] == nums[l+1]) {
l++;
}
//去重,因为 i不变,当此时 r 取的数的值与前一个相同,所以不用在计算
while(l< r && nums[r] == nums[r-1]){
r--;
}
//将 左指针右移,将右指针左移。
l++;
r--;
//如果结果小于0,将左指针右移
}else if(sum < 0){
l++;
//如果结果大于0,将右指针左移
}else if(sum > 0){
r--;
}
}
}
return res;
}
};
16题
与15题大体相同
- 对数组进行排序
- 先用ans获取1 2 3的和
- 循环i=0;i<len;i++ 定义 l =i+1 h=len-1
- 在 l<h的前提下
- 比较target-sum 和target-ans的绝对值大小 如果小于则 ans=sum
- 比较sum和target的大小 如果大于则h-- 小于则l++
- 如果相等就直接返回ans
4.返回ans
class Solution {
public:
int threeSumClosest(vector<int>& nums, int target) {
int len=nums.size();
sort(nums.begin(),nums.end());
int ans=nums[0]+nums[1]+nums[2];
for(int i=0;i<len;i++){
int l=i+1;
int h=len-1;
while(l<h){
int sum=nums[i]+nums[l]+nums[h];
if(abs(target-sum)<abs(target-ans)){
ans=sum;
}
if(sum>target){
h--;
}
else if(sum<target){
l++;
}
else {
return ans;
}
}
}
return ans;
}
};
18题
与15题大致相同 对数组进行排序 然后去重
c++
class Solution {
public:
vector<vector<int>> fourSum(vector<int>& nums, int target) {
vector<vector<int> > res;
int len=nums.size();
sort(nums.begin(),nums.end());
if(len<4)
return res;
for(int i=0;i<len-3;i++){
if(i > 0 && nums[i] == nums[i-1]) continue;
for(int l=i+1;l<len-2;l++){
if(l>i+1 && nums[l]==nums[l-1]) continue;
int s=l+1;
int h=len-1;
while(s<h){
if(nums[i]+nums[l]-target>-(nums[s]+nums[h])){
h--;
}
else if(nums[i]+nums[l]-target<-(nums[s]+nums[h])){
s++;
}
else
{
res.push_back({nums[i],nums[l],nums[s],nums[h]});
while(s<h && nums[s]==nums[s+1])
s++;
while(s<h && nums[h]==nums[h-1])
h--;
s++;
h--;
}
}
}
}
return res;
}
};
js
var fourSum = function(nums, target) {
const quadruplets = [];
if (nums.length < 4) {
return quadruplets;
}
nums.sort((x, y) => x - y);
const length = nums.length;
for (let i = 0; i < length - 3; i++) {
if (i > 0 && nums[i] === nums[i - 1]) {
continue;
}
if (nums[i] + nums[i + 1] + nums[i + 2] + nums[i + 3] > target) {
break;
}
if (nums[i] + nums[length - 3] + nums[length - 2] + nums[length - 1] < target) {
continue;
}
for (let j = i + 1; j < length - 2; j++) {
if (j > i + 1 && nums[j] === nums[j - 1]) {
continue;
}
if (nums[i] + nums[j] + nums[j + 1] + nums[j + 2] > target) {
break;
}
if (nums[i] + nums[j] + nums[length - 2] + nums[length - 1] < target) {
continue;
}
let left = j + 1, right = length - 1;
while (left < right) {
const sum = nums[i] + nums[j] + nums[left] + nums[right];
if (sum === target) {
quadruplets.push([nums[i], nums[j], nums[left], nums[right]]);
while (left < right && nums[left] === nums[left + 1]) {
left++;
}
left++;
while (left < right && nums[right] === nums[right - 1]) {
right--;
}
right--;
} else if (sum < target) {
left++;
} else {
right--;
}
}
}
}
return quadruplets;
};
11.盛最多水的容器
思想:双指针夹逼
用双指针i,j循环height数,i,j对应高度较小的那个先向内移动,不断计算面积,更新最大面积
/**
* @param {number[]} height
* @return {number}
*/
var maxArea = function(height) {
const len=height.length;
let max=0;
for(let i=0,j=len-1;i<j;){
let minheight=height[i]<height[j]?height[i++]:height[j--];
let res=minheight*(j-i+1);
max=Math.max(max,res);
}
return max;
};