15. 三数之和
给定一个包含 n 个整数的数组 nums
,判断 nums
中是否存在三个元素 a,b,c ,使得 a + b + c = 0 ?找出所有满足条件且不重复的三元组。
注意:答案中不可以包含重复的三元组。
例如, 给定数组 nums = [-1, 0, 1, 2, -1, -4], 满足要求的三元组集合为: [ [-1, 0, 1], [-1, -1, 2] ]
您是否在真实的面试环节中遇到过这道题目呢?
错误答案1(耗时太长):
class Solution {
public:
vector<vector<int>> threeSum(vector<int>& nums) {
vector<int> tmp;
vector<vector<int>> res;
int len = nums.size();
int t,t1,t2,t3;
if(3>nums.size()){return res;}
for(int i=0;i<len;i++)
{
for(int j=i+1;j<len;j++)
{
for(int k=j+1;k<len;k++)
{
if(0==nums[i]+nums[j]+nums[k])
{
t1=nums[i];
t2=nums[j];
t3=nums[k];
if(t1>t2)
{
t=t2;
t2=t1;
t1=t;
}
if(t2>t3)
{
t=t3;
t3=t2;
t2=t;
}
if(t1>t2)
{
t=t2;
t2=t1;
t1=t;
}
tmp.clear();
tmp.push_back(t1);
tmp.push_back(t2);
tmp.push_back(t3);
if(0!=res.size())
{
t=0;
for(int n=0;n<res.size();n++)
{
if(tmp == res[n])
{
t = 1;
break;
}
}
if(!t)
{
res.push_back(tmp);
}
}
else
{
res.push_back(tmp);
}
}
}
}
}
return res;
}
};
提交记录
311 / 313 个通过测试用例 | 状态:
超出时间限制 |
提交时间:0 分钟之前 |
最后执行的输入: [82597,-9243,62390,83030,-97960,-26521,-61011,83390,-38677,12333,75987,46091,83794,19355,-71037,-6242,-28801,324......
我的答案2:
class Solution {
public:
vector<vector<int>> threeSum(vector<int>& nums) {
vector<int> tmp;
vector<vector<int>> res;
int len = nums.size();
int t,t1,t2,t3;
vector<int>::iterator iter_i;
vector<int>::iterator iter_j;
vector<int>::iterator iter_k;
vector<vector<int>>::iterator iter_res;
iter_i = nums.begin();
for(int i=0;i<len;i++)
{
iter_j = nums.begin();
iter_j += i+1;
for(int j=i+1;j<len;j++)
{
iter_k = nums.begin();
iter_k += j+1;
for(int k=j+1;k<len;k++)
{
if(0==*iter_i+*iter_j+*iter_k)
{
t1=*iter_i;
t2=*iter_j;
t3=*iter_k;
if(t1>t2)
{
t=t2;
t2=t1;
t1=t;
}
if(t2>t3)
{
t=t3;
t3=t2;
t2=t;
}
if(t1>t2)
{
t=t2;
t2=t1;
t1=t;
}
tmp.clear();
tmp.push_back(t1);
tmp.push_back(t2);
tmp.push_back(t3);
if(0!=res.size())
{
t=0;
for(iter_res = res.begin();iter_res!=res.end();iter_res++)
{
if(tmp == *iter_res)
{
t = 1;
break;
}
}
if(!t)
{
res.push_back(tmp);
}
}
else
{
res.push_back(tmp);
}
}
iter_k++;
}
iter_j++;
}
iter_i++;
}
return res;
}
};
依旧是超出时间限制!!
于是乎在网上找了参考答案:
来源:https://blog.youkuaiyun.com/shinanhualiu/article/details/48913435
思路:solution:
因为三元组的元素是按照递增的顺序,因此我们首先需要对S进行排序。然后保持两个前后索引来进行比较。
class Solution {
public:
/**
* @param numbers : Give an array numbers of n integer
* @return : Find all unique triplets in the array which gives the sum of zero.
*/
vector<vector<int> > threeSum(vector<int> &nums) {
// write your code here
vector<vector<int>> res;
sort(nums.begin(), nums.end()); //对数组进行排序
int i = 0 , last = nums.size()-1;
while (i < last) {
int a = nums[i], j = i + 1, k = last;
while (j < k) {
int b = nums[j], c = nums[k];
int sum = a + b + c;
if (sum == 0) res.push_back({a,b,c});
if (sum <= 0) //注意不能含有相同的索引
while (nums[j] == b && j < k ) ++j;
if (sum >= 0)
while (nums[k] == c && j < k) --k;
}
while (nums[i] == a && i < last) ++i;
}
return res;
}
};
果然没有好好思考出最好的方式,做了很多已然一看就和不会为0的遍历,真是笨 = = ;