组合总和
给定一个无重复元素的数组 candidates 和一个目标数 target ,找出 candidates 中所有可以使数字和为 target 的组合。
candidates 中的数字可以无限制重复被选取。
说明:
所有数字(包括 target)都是正整数。
解集不能包含重复的组合。
示例 1:
输入: candidates = [2,3,6,7], target = 7,
所求解集为:
[
[7],
[2,2,3]
]
思路和代码
还是递归回溯的问题,就是不断的加入,递归,再撤销加入
class Solution {
public:
vector<vector<int>> combinationSum(vector<int>& candidates, int target) {
vector<vector<int>> res;
vector<int> temp;
core(candidates, target, 0, temp, res);
return res;
}
void core(vector<int>& candidates, int target, int start, vector<int>& temp, vector<vector<int>>& res){
if(target == 0){
res.push_back(temp);
return ;
}
for(int i=start; i<candidates.size(); i++){
if(candidates[i] > target)
continue;
temp.push_back(candidates[i]);
core(candidates, target-candidates[i], i, temp, res);
temp.pop_back();
}
}
};
组合总和2
相比于上一题,上一题是可以重复使用数字的,但这一题不行,而且还包含重复元素。
只需要在for循环里再加入一个判断即可。
class Solution {
public:
vector<vector<int>> combinationSum2(vector<int>& num, int target) {
vector<vector<int>> res;
vector<int> out;
sort(num.begin(), num.end());
helper(num, target, 0, out, res);
return res;
}
void helper(vector<int>& num, int target, int start, vector<int>& out, vector<vector<int>>& res) {
if (target < 0) return;
if (target == 0) { res.push_back(out); return; }
for (int i = start; i < num.size(); ++i) {
if (i > start && num[i] == num[i - 1]) continue;
out.push_back(num[i]);
helper(num, target - num[i], i + 1, out, res);
out.pop_back();
}
}
};