题目地址:
https://leetcode.com/problems/combination-sum-ii/
描述:
Given a collection of candidate numbers (candidates) and a target number (target), find all unique combinations in candidates where the candidate numbers sums to target.
Each number in candidates may only be used once in the combination.
Note:
All numbers (including target) will be positive integers.
The solution set must not contain duplicate combinations.
分析:
简单做法就是用递归,用python实现了,见代码1。需要注意有注释的那行,保障了not contain duplicate combinations.
又考虑了非递归做法,用cpp实现了(好久不用cpp,就当复习了),见代码2。
代码1:
class Solution(object):
def combinationSum2(self, candidates, target):
"""
:type candidates: List[int]
:type target: int
:rtype: List[List[int]]
"""
candidates.sort()
result = []
one = []
def recursion(idx, sum):
for x in range(idx, len(candidates)):
if x != idx and candidates[x] == candidates[x - 1]: # 同一个slot,不放入相同的值
continue
one.append(candidates[x])
sum = _sum = sum + candidates[x]
if _sum < target:
recursion(x + 1, sum)
elif sum == target:
result.append(one[:])
t = one.pop()
sum -= t
if _sum >= target:
break
recursion(0, 0)
return result
代码2:
class Solution {
public:
vector<vector<int>> combinationSum2(vector<int>& candidates, int target) {
vector<vector<int>> result;
vector<int> idxs;
int idx = 0;
int sum = 0;
sort(candidates.begin(), candidates.end());
idxs.push_back(idx);
sum += candidates[idx];
do {
bool is_push = true;
if (sum >= target) { // 1.继续push的话会超过target
if (sum == target) {
vector<int> tmp;
for (auto iter = idxs.begin(); iter != idxs.end(); iter++)
tmp.push_back(candidates[*iter]);
result.push_back(tmp);
}
is_push = false;
}
idx = idxs.back(); // 2. 没有可以push的数了
if (idx == candidates.size() - 1)
is_push = false;
if (is_push) { // 继续push
idxs.push_back(idx + 1);
sum += candidates[idx + 1];
}
else { // pop队尾,直到队尾可以修改为合理值
while (idxs.size()) {
sum -= candidates[idxs.back()];
idxs.pop_back();
if (idxs.size()) {
idx = idxs.back();
if (candidates[idx] != candidates.back()) {
do {
idx++;
} while (candidates[idx] == candidates[idx - 1]);
break;
}
}
}
if (idxs.size()) {
sum -= candidates[idxs.back()];
idxs[idxs.size() - 1] = idx;
sum += candidates[idx];
}
}
} while (idxs.size());
return result;
}
};
最后!吐槽下现在的CSDN #¥%……&*