https://leetcode.com/problems/3sum-closest/
Given an array
nums
of n integers and an integertarget
, find three integers innums
such that the sum is closest totarget
. 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).
题目本身很简单,使用和3sum同样的方法就可以,问题的重点同样在与细节的优化
但是注意,在看了最快的提交代码之后发现其中有一处错误,他在最外层循环中直接使用了 if (nums[k] - target > dist) break;来剪枝,乍看之下好像没什么问题(nums[k]已经大于了当前解的上界,而[i][j]只会比[k]更大),但是细想之后就会发现当tar+dis<0时并不能保证后续不会出现更优解(反例:[-5,-4,-3,-2,0], -6,当k=1时)。
我的代码:
class Solution {
public:
int threeSumClosest(vector<int>& nums, int target) {
int re_dif = INT_MAX;
int tem;
int len = nums.size();
int cur;
sort(nums.begin(), nums.end());
for(int i = 0; i < len; ++i){
cur = nums[i]-target;
// cout << i << ' ' << cur << endl;
int lo = i+1;
int hi = len-1;
while(lo < hi){
tem = cur+nums[lo]+nums[hi];
// cout << i << ' ' << lo << ' ' << hi << ' ' << tem << endl;
if(abs(tem) < abs(re_dif)) re_dif = tem;
if(tem > 0) --hi;
else if(tem < 0) ++lo;
else{
return target;
}
}
}
return target+re_dif;
}
};
问题代码:
class Solution {
public:
int threeSumClosest(vector<int>& nums, int target) {
int dist = INT_MAX, res;
sort(nums.begin(), nums.end());
if (nums.size() < 3) return 0;
for (int k = 0; k < nums.size()-2; ++k) {
if (nums[k] - target > dist) break; //就是这一句判断有问题
if (k > 0 && nums[k] == nums[k - 1]) continue;
int i = k + 1, j = nums.size() - 1, sum;
while (i < j) {
sum = nums[k] + nums[i] + nums[j];
if (sum == target)
return sum;
else {
if (abs(sum - target) < dist) {
dist = abs(sum - target);
res = sum;
}
if (sum < target) ++i;
else --j;
}
}
}
return res;
}
};