您的位置:首页 > 其它

Leetcode 39 40 216 Combination Sum I II III

2016-04-06 21:18 435 查看
CombinationSumGivenasetofcandidatenumbers(C)andatargetnumber(T),findalluniquecombinationsinCwherethecandidatenumberssumstoT.ThesamerepeatednumbermaybechosenfromCunlimitednumberoftimes.Note:Allnumbers(includingtarget)willbepositiveintegers.Elementsinacombination(a1,a2,…,ak)mustbeinnon-descendingorder.(ie,a1≤a2≤…≤ak).Thesolutionsetmustnotcontainduplicatecombinations.Forexample,givencandidateset
2,3,6,7
andtarget
7
,
Asolutionsetis:
[7]

[2,2,3]
思路:需要回溯的思想。对数组里面的每个数,用递归的方式叠加,每次递归将和sum与target作比较,若相等则加入结果list,sum>target则舍弃,并返回false,若sum<target,则继续进行递归。第一种sum=target的情况下,在加入结果list后,要将当前一种结果最后加入的元素remove,并继续对后面的元素进行递归;在第二种sum>target的情况下,则需要将当前结果的最后加入的两个元素remove,并继续对后面的元素进行递归。第三种情况sum<target,无需删除直接递归。注意元素可以重复,所以下一次递归是从当前递归元素开始。
publicclassS039{
//backtracking--回溯算法
publicList<List<Integer>>combinationSum(int[]candidates,inttarget){
List<List<Integer>>result=newArrayList<List<Integer>>();
List<Integer>temp=newArrayList<Integer>();
Arrays.sort(candidates);//很关键的一步
findConbination(result,temp,0,0,target,candidates);
returnresult;
}
publicbooleanfindConbination(List<List<Integer>>result,List<Integer>temp,intsum,intlevel,inttarget,int[]candidates){
if(sum==target){
result.add(newArrayList<>(temp));//从内存复制,防止后面的改变对其发生影响
returntrue;
}elseif(sum>target){
returnfalse;
}else{
for(inti=level;i<candidates.length;i++){//思考level参数的作用
temp.add(candidates[i]);
//sum+=candidates[i];思考这一行注释掉并把sum的增加加在下一行参数里面的原因
if(!findConbination(result,temp,sum+candidates[i],i,target,candidates)){//i表示下一次递归从当前递归的位置开始
i=candidates.length;
}
temp.remove(temp.size()-1);
}
returntrue;
}
}
}
CombinationSumIIGivenacollectionofcandidatenumbers(C)andatargetnumber(T),findalluniquecombinationsinCwherethecandidatenumberssumstoT.EachnumberinCmayonlybeusedonceinthecombination.Note:Allnumbers(includingtarget)willbepositiveintegers.Elementsinacombination(a1,a2,…,ak)mustbeinnon-descendingorder.(ie,a1≤a2≤…≤ak).Thesolutionsetmustnotcontainduplicatecombinations.Forexample,givencandidateset
10,1,2,7,6,1,5
andtarget
8
,
Asolutionsetis:
[1,7]

[1,2,5]

[2,6]

[1,1,6]
思路:与前一题的不同之处在于结果要求同一位置的元素只能出现一次,但是值相同在数组中位置不同的元素可以同时出现。与前一题的不同就是下一次递归都是从当前递归的下一个元素开始。另外测试集不相同,前一题的测试集中不会出现同一数组中有相同的元素,所以不用额外去重。这一题同一数组会出现相同元素,所以得在元素向前移的时候跳过相同的元素来进行去重。
publicclassS040{
publicList<List<Integer>>combinationSum2(int[]candidates,inttarget){
Arrays.sort(candidates);
List<List<Integer>>rets=newArrayList<List<Integer>>();
List<Integer>ret=newArrayList<Integer>();
find(candidates,0,0,target,rets,ret);
returnrets;
}
publicstaticbooleanfind(int[]candidates,intsum,intlevel,inttarget,List<List<Integer>>rets,List<Integer>ret){
if(sum==target){
rets.add(newArrayList<>(ret));
returntrue;
}elseif(sum>target){
returnfalse;
}else{
for(inti=level;i<candidates.length;i++){
ret.add(candidates[i]);
if(!find(candidates,sum+candidates[i],i+1,target,rets,ret)){//i+1表明下一次递归从当前递归的下一位元素开始
i=candidates.length;
}
//去重
while(i<candidates.length-1&&ret.get(ret.size()-1)==candidates[i+1]){
i++;
}
ret.remove(ret.size()-1);
}
returntrue;
}
}
}
CombinationSumIIIFindallpossiblecombinationsofknumbersthatadduptoanumbern,giventhatonlynumbersfrom1to9canbeusedandeachcombinationshouldbeauniquesetofnumbers.Ensurethatnumberswithinthesetaresortedinascendingorder.Example1:Input:k=3,n=7Output:
[[1,2,4]]
Example2:Input:k=3,n=9Output:
[[1,2,6],[1,3,5],[2,3,4]]

思路:这一题还是参照了前两题,相当于把前两题中的candidates数组变为nums={1,2,3,4,5,6,7,8,9},然后再在每一次比较结果时加上结果list大小的比较,当前list的大小不超过k。
也不用额外去重。
publicclassS216{
publicList<List<Integer>>combinationSum3(intk,intn){
List<List<Integer>>result=newArrayList<List<Integer>>();
List<Integer>temp=newArrayList<Integer>();
if(n<k*(k+1)/2||n>45||k>9||k<1){
returnresult;
}
int[]nums={1,2,3,4,5,6,7,8,9};
find(nums,k,n,0,0,result,temp);
returnresult;
}
publicstaticbooleanfind(int[]nums,intk,intn,intsum,intlevel,
List<List<Integer>>result,List<Integer>temp){
if(temp.size()>k||sum>n){
returnfalse;
}elseif(sum==n&&temp.size()==k){
result.add(newArrayList<>(temp));
returntrue;
}else{
for(inti=level;i<nums.length;i++){
temp.add(nums[i]);
if(!find(nums,k,n,sum+nums[i],i+1,result,temp)){
i=nums.length;
}
temp.remove(temp.size()-1);
}
returntrue;
}
}
}


                                            
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: