import java.util.ArrayList; import java.util.Arrays; import java.util.List; /** * Given a set of candidate numbers (C) (without duplicates) 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. 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] ] 回溯法,每次递归传入的目标值是当前目标值减去此次添加的值,递归函数每次先检测传入的目标值是否是0 如果是就添加到list中,由于没有负数存在,直接return就行。如果不是,那就遍历数组,要设定一个index记录当前遍历到 那个数了,递归中的遍历都是从index开始,这样可以避免重复数组的出现。当现在遍历到的数比当前目标值小就递归, 每次递归结束都要回溯(list删除上一个数);如果比目标值大了,由于数组已经排序,所以可以直接break。 */ public class Q39CombinationSum { public static void main(String[] args) { int[] nums = new int[]{41,24,30,47,40,27,21,20,46,48,23,44,25,49,35,42,36,28,33,32,29,22,37,34,26,45}; System.out.println(combinationSum(nums,53)); } public static List<List<Integer>> combinationSum(int[] candidates, int target) { Arrays.sort(candidates); List<List<Integer>> result = new ArrayList<>(); backTracking(result,candidates,new ArrayList<>(),target,0); return result; } public static void backTracking(List<List<Integer>> result,int[] candidates, List<Integer> cur,int left,int index) { if(left == 0) { result.add(new ArrayList<>(cur)); return; } for(int i = index;i < candidates.length;i++) { if (candidates[i] <= left) { cur.add(candidates[i]); backTracking(result,candidates,cur,left-candidates[i],i); cur.remove(cur.size()-1); } else break; } } }