1. 程式人生 > >leetcode:組合總和(java回溯)

leetcode:組合總和(java回溯)

package LeetCode;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

/*
給定一個無重複元素的陣列 candidates 和一個目標數 target ,找出 candidates 中所有可以使數字和為 target 的組合。
candidates 中的數字可以無限制重複被選取。
說明:
所有數字(包括 target)都是正整數。
解集不能包含重複的組合。
示例 1:
輸入: candidates = [2,3,6,7], target = 7,
所求解集為:
[
  [7],
  [2,2,3]
]
 */
public class CombinationSum {
    public List<List<Integer>> combinationSum(int[] candidates, int target) {
        List<Integer> resluts = new ArrayList<>();
        Arrays.sort(candidates);
        List<List<Integer>> result = new ArrayList<>();
        combinationSumhuisu(candidates, target, resluts,0,result);
        return result;
    }

    public static void combinationSumhuisu(int[] candidates, int target, List<Integer> results,int start,List<List<Integer>> result) {

            //判斷是否可以整減
            if(target<0){
                return ;
            }else  if (target == 0) {
                //指向一塊新的不變的地址否則result會隨著results改變而改變
                result.add(new ArrayList<Integer>(results));
                return;
            } else
                //start防止了i=2然後遞迴後i=1重複i=1 遞迴i=2時所以要固定其i
                for (int i = start; i < candidates.length; i++) {
                //判斷target是否可以減掉candidates
                    results.add(candidates[i]);
                    combinationSumhuisu(candidates, target-candidates[i], results,i,result);
                    results.remove(results.size()-1);
        }
    }

    public static void main(String[] args) {
        int[] a = {2, 3, 6, 7};
        int tage = 7;
        CombinationSum b = new CombinationSum();
        System.out.println(b.combinationSum(a, tage));
    }
}