【LeetCode】18_4Sum

题目

4Sum

 

Given an array S of n integers, are there elements abc, and d in S such that a + b + c + d = target? Find all unique quadruplets in the array which gives the sum of target.

Note:

  • Elements in a quadruplet (a,b,c,d) must be in non-descending order. (ie, a ≤ b ≤ c ≤ d)
  • The solution set must not contain duplicate quadruplets.

    For example, given array S = {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)

解析

还是那一套类似的。


前两个进行循环,后两个查找固定和即可。

我的代码如下

结果报错了,超时。

class Solution {
public:
    vector<vector<int>> fourSum(vector<int>& nums, int target) {
		vector<vector<int>> ret;
		if(nums.size()<4)
		return ret;
		sort(nums.begin(), nums.end());  
		for (int i = 0; i<nums.size()-3; i++)
		{
			if (i>0 && nums.at(i)==nums.at(i-1))
			{
				continue;
			}
			for (int j = i+1; j<nums.size()-2;j++)
			{
				if (j>i+1 && nums.at(j)==nums.at(j-1))
				{
					continue;
				}
				int m = j+1;
				int n = nums.size()-1;
				while (m<n)
				{
					if (nums.at(i)+nums.at(j)+nums.at(m)+nums.at(n) > target)
					{
						n--;
						while (m<n && nums.at(n) == nums.at(n+1))
						n--;
					}
					else if (nums.at(i)+nums.at(j)+nums.at(m)+nums.at(n) < target)
					{
						m++;
						while (m<n && nums.at(m)==nums.at(m-1))
						m++;
					}
					else
					{
						vector<int> tmp;
						tmp.push_back(nums.at(i));
						tmp.push_back(nums.at(j));
						tmp.push_back(nums.at(m));
						tmp.push_back(nums.at(n));
						ret.push_back(tmp);
						n--;
						m++;
						while (m<n && nums.at(n)==nums.at(n+1))
							n--;
						while (m<n && nums.at(m)==nums.at(m-1))
							m++;
					}
				}
			}
		}
		return ret;
    }
    
};
看看大神的吧。

 vector<vector<int> > fourSum(vector<int> &num, int target) {  
        vector<vector<int>> out;  
        set<vector<int>> res;  
        if (num.size() < 4)  
            return out;  
        sort(num.begin(), num.end());  
        for (int i=0; i<num.size()-3; i++)  
        {  
              
            for (int j =i+1;j<num.size()-2;j++)  
            {  
                int begin = j+1;  
                int end = num.size()-1;  
                while(begin < end){  
                    int sum = num[i] + num[j] + num[begin] + num[end];  
                    if (sum== target)  
                    {  
                        vector<int> tmp;  
                        tmp.push_back(num[i]);  
                        tmp.push_back(num[j]);  
                        tmp.push_back(num[begin]);  
                        tmp.push_back(num[end]);  
                        res.insert(tmp);  
                        begin++;  
                        end--;  
                    }   
                    else if(sum < target)  
                    {  
                        begin++;  
                    }else{  
                        end--;  
                    }  
                }  
                  
            }  
        }  
         set<vector<int>>::iterator it = res.begin();    
        for(; it != res.end(); it++)    
            out.push_back(*it);   
  
  
    }  

用集合来去除重复元素的思想确实很赞。

我把自己代码里也改成使用set,结果还是超时!

于是我把自己代码里的nums.at(i)全部改成了nums[i]于是就accept了。看来这个非常影响性能。可能跟at会进行边界检查有关系。在实际使用中使用at比较好,越界会出错。而[]则行为未定义。

不过,在刷题中:[]的效率比at高,这个需要记住。

改正后如下

class Solution {
public:
    vector<vector<int>> fourSum(vector<int>& nums, int target) {
		vector<vector<int>> ret;
		set<vector<int>> res;
		if(nums.size()<4)
			return ret;
		sort(nums.begin(), nums.end());  
		for (int i = 0; i<nums.size()-3; i++)
		{
			for (int j = i+1; j<nums.size()-2;j++)
			{
				int m = j+1;
				int n = nums.size()-1;
				while (m<n)
				{
					int sum = nums[i]+nums[j]+nums[m]+nums[n];
					if ( sum > target)
					{
						n--;
					}
					else if (sum < target)
					{
						m++;
					}
					else
					{
						vector<int> tmp;
						tmp.push_back(nums[i]);
						tmp.push_back(nums[j]);
						tmp.push_back(nums[m]);
						tmp.push_back(nums[n]);
						res.insert(tmp);
						n--;
						m++;
					}
				}
			}
		}
		set<vector<int>>::iterator it = res.begin();
		for (;it != res.end();it++)
		{
			ret.push_back(*it);
		}
		return ret;
    }
    
};










评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值