combination sum leetcode
Given a set of candidate numbers (C) and a target number (T), find all unique combinations in C where the candidate numbers sums to T.
The same repeated number may be chosen from C unlimited number of times.
Note:
- All numbers (including target) will be positive integers.
- Elements in a combination (a1, a2, … , ak) must be in non-descending order. (ie, a1 ≤ a2 ≤ … ≤ ak).
- The solution set must not contain duplicate combinations.
For example, given candidate set 2,3,6,7
and target 7
,
A solution set is: [7]
[2, 2, 3]
这个题目是个backtrack的问题,这个问题,也类似于printtree中path等于固定值的解法。
其中最有意思的一个trick是 记录访问过路径的index[] 以及那个对应的position。我的第一想法是直接用一个vector来记录路径,进来一个push,回退一个popback。
最后发现这是个很笨拙的方法。最好的办法是,用一个数组index 来记录位置,用递归的层数来做索引,将简单很多。
具体这个题目,两种思路,一个是sum的方法,从sum=0 开始,把整个数组内容递归的加一遍,知道发现target,那就把路径输出。
另外一个办法是减法,
void Find(vector<int> &candidates, int sum, int target, int* index, int start) { int size = candidates.size(); if (sum>target) return; if (sum == target) { vector<int> result; for (int i = 1; i<= start; i++) { result.push_back(candidates[index[i]]); } sort(result.begin(), result.end()); finalresult.push_back(result); return; } for (int k = index[start]; k< size; k++) { index[start + 1] = k; Find(candidates, sum + candidates[k], target, index, start + 1); } } vector<vector<int> > combinationSum(vector<int> &candidates, int target) { int index[1024]; index[0] = 0; int start = 0; int sum = 0; Find(candidates, sum, target, index, start); return finalresult; }
减法
vector<vector<int>> finalresult; void getcombine(vector<int>candidates, int target, int* index, int start) { int len = candidates.size(); if (target<candidates[0])//the target not fall inside means the sequence is wrong. { return; } else { for (int i = index[start]; i < len; i++) { index[start + 1] = i; if (candidates[i] == target)// find it { vector<int> result; //get output from index for (int n = 1; n <= start+1; n++) { result.push_back(candidates[index[n]]); } finalresult.push_back(result); return; } getcombine(candidates, target - candidates[i], index, start+1); } } } vector<vector<int> > combinationSumnew(vector<int> &candidates, int target) { vector<int> result; int index[1024]; index[0] = 0; int start = 0; getcombine(candidates, target, index, start); return finalresult; }