C++ 组合和
给定一组候选数(C)和一个目标数(T),找出C中候选数和T之和的所有唯一组合 相同的重复次数可从C中选择,次数不限 例如, 给定候选集C++ 组合和,c++,recursion,combinations,backtracking,C++,Recursion,Combinations,Backtracking,给定一组候选数(C)和一个目标数(T),找出C中候选数和T之和的所有唯一组合 相同的重复次数可从C中选择,次数不限 例如, 给定候选集2,3,6,7和目标7, 解决方案集是: [2,2,3] [7] 解决方案代码为: class Solution { public: void doWork(vector<int> &candidates, int index, vector<int> ¤t, int currentSum,
2,3,6,7
和目标7
,
解决方案集是:
[2,2,3]
[7]
解决方案代码为:
class Solution {
public:
void doWork(vector<int> &candidates, int index, vector<int> ¤t, int currentSum, int target, vector<vector<int> > &ans) {
if (currentSum > target) {
return;
}
if (currentSum == target) {
ans.push_back(current);
return;
}
for (int i = index; i < candidates.size(); i++) {
current.push_back(candidates[i]);
currentSum += candidates[i];
doWork(candidates, i, current, currentSum, target, ans);
current.pop_back();
currentSum -= candidates[i];
}
}
vector<vector<int>> combinationSum(vector<int> &candidates, int target) {
vector<int> current;
vector<vector<int> > ans;
sort(candidates.begin(), candidates.end());
vector<int> uniqueCandidates;
for (int i = 0; i < candidates.size(); i++) {
if (i == 0 || candidates[i] != candidates[i-1]) {
uniqueCandidates.push_back(candidates[i]);
}
}
doWork(uniqueCandidates, 0, current, 0, target, ans);
return ans;
}
};
类解决方案{
公众:
无效工作(向量和候选项、整数索引、向量和当前、整数当前和、整数目标、向量和ans){
如果(currentSum>目标){
返回;
}
如果(currentSum==目标){
ans.推回(当前);
返回;
}
for(int i=index;i
现在,虽然我可以通过一个例子来理解这个解决方案,但我自己怎么能得出这样的解决方案呢。此功能的主要工作如下:
for (int i = index; i < candidates.size(); i++) {
current.push_back(candidates[i]);
currentSum += candidates[i];
doWork(candidates, i, current, currentSum, target, ans);
current.pop_back();
currentSum -= candidates[i];
}
for(int i=index;i
请告诉我如何理解上述代码以及如何思考解决方案。我可以解决基本的递归问题,但这些问题看起来遥不可及。感谢您的时间。因此,代码的基本功能是:
- 继续添加相同的数字,直到总和大于或等于目标值
- 如果相等,则保存组合
- 如果较大,则删除最后添加的数字(返回上一步),并开始将集合中的下一个数字添加到总和
候选人:{2,2,1}
目标:4
排序和删除重复项会将集合更改为{1,2}。递归的顺序为:
- 总和=1;
- 总和=1+1;
- 总和=1+1+1;
- 总和=1+1+1+1;(与目标相同,保存组合)
- 总和=1+1+1+2;(大于目标,无需添加更多数字)
- 总和=1+1+2;(保存组合,无需添加更多数字)
- 总和=1+1+1;
- 总和=1+2;
- 总和=1+2+2;(大一点,没有更多的数字)
- 总和=1+1;
- 总和=2;
- 总和=2+2;(保存,这是最后一次递归)
for (int i = index; i < candidates.size(); i++) {
current.push_back(candidates[i]);
currentSum += candidates[i];
doWork(candidates, i, current, currentSum, target, ans);
current.pop_back();
currentSum -= candidates[i];
}