40. 组合总和 II
难度中等424收藏分享切换为英文接收动态反馈
给定一个数组 candidates
和一个目标数 target
,找出 candidates
中所有可以使数字和为 target
的组合。
candidates
中的每个数字在每个组合中只能使用一次。
说明:
- 所有数字(包括目标数)都是正整数。
- 解集不能包含重复的组合。
示例 1:
输入: candidates = [10,1,2,7,6,1,5], target = 8,
所求解集为:
[
[1, 7],
[1, 2, 5],
[2, 6],
[1, 1, 6]
]
示例 2:
输入: candidates = [2,5,2,1,2], target = 5,
所求解集为:
[
[1,2,2],
[5]
]
通过次数112,924
提交次数174,967
题解
class Solution {
public List<List<Integer>> combinationSum2(int[] candidates, int target) {
List<List<Integer>> res = new LinkedList<>();
if(candidates == null || candidates.length ==0) return res;
Arrays.sort(candidates);
traceBack(candidates, 0, target, 0, new LinkedList<Integer>(), res);
return res;
}
void traceBack(int[] candidates, int sum, int target, int start, LinkedList<Integer> temp, List<List<Integer>> res){
if( sum == target){
res.add( new LinkedList<>(temp));
return;
}
for(int i =start; i < candidates.length; i++){
if(sum >target) break;
if( i > start && candidates[i] == candidates[i-1]) continue;
temp.add(candidates[i]);
sum+=candidates[i];
traceBack(candidates, sum, target, i+1, temp, res);
temp.pollLast();
sum-=candidates[i];
}
}
}
不考虑时间复杂度
利用 contains()
来对结果进行判重
class Solution {
public List<List<Integer>> combinationSum2(int[] candidates, int target) {
List<List<Integer>> res = new LinkedList<>();
if(candidates == null || candidates.length ==0) return res;
Arrays.sort(candidates);
traceBack(candidates, 0, target, 0, new LinkedList<Integer>(), res);
return res;
}
void traceBack(int[] candidates, int sum, int target, int start, LinkedList<Integer> temp, List<List<Integer>> res){
if( sum == target && !res.contains(temp)){
res.add( new LinkedList<>(temp));
return;
}
for(int i =start; i < candidates.length; i++){
if(sum >target) break;
temp.add(candidates[i]);
sum+=candidates[i];
traceBack(candidates, sum, target, i+1, temp, res);
temp.pollLast();
sum-=candidates[i];
}
}
}
参考:
转载请注明来源,欢迎对文章中的引用来源进行考证,欢迎指出任何有错误或不够清晰的表达。可以在下面评论区评论,也可以邮件至 mym_74@163.com