组合问题

77. 组合

给定两个整数 n 和 k,返回 1 ... n 中所有可能的 k 个数的组合。
示例:
输入: n = 4, k = 2输出:[ [2,4], [3,4],[2,3],[1,2],[1,3],[1,4],]
class Solution {
    List<List<Integer>> res=new ArrayList<>();
    public List<List<Integer>> combine(int n, int k) {
        List<Integer> c=new ArrayList<>();
        helper(n,k,1,c);
        return res;
    }
    public void helper(int n,int k,int start,List<Integer> c)
    {
        if(c.size()==k)
        {
            List<Integer> temp=new ArrayList<>(c);
            res.add(temp);
            return ;
        }
        if()
        for(int i=start;i<=n-(k-c.size())+1;i++)
        {
            c.add(i);
            helper(n,k,i+1,c);
            c.remove(c.size()-1);
        }
        return ;
    }
}

39. 组合总和

给定一个无重复元素的数组 candidates 和一个目标数 target ,找出 candidates 中所有可以使数字和为 target 的组合。

candidates 中的数字可以无限制重复被选取。

说明:所有数字(包括 target)都是正整数。  解集不能包含重复的组合。

class Solution {
    private List<List<Integer>> res=new ArrayList<>();
    public List<List<Integer>> combinationSum(int[] candidates, int target) {
        Arrays.sort(candidates);
        List<Integer> list=new ArrayList<>();
        helper(candidates,0,target,list);
        return res;
    }
    public void helper(int[] nums,int start,int target,List<Integer> list)
    {
        if(target==0)
        {
            res.add(new ArrayList<>(list));
            return ;
        }
        for(int i=start;i<nums.length&&nums[i]<=target;i++)
        {
            list.add(nums[i]);
            target-=nums[i];
            helper(nums,i,target,list);
            target+=nums[i];
            list.remove(list.size()-1);
        }
        return ;
        
    }
}

40. 组合总和 II

给定一个数组 candidates 和一个目标数 target ,找出 candidates 中所有可以使数字和为 target 的组合。

candidates 中的每个数字在每个组合中只能使用一次。

说明:  所有数字(包括目标数)都是正整数。解集不能包含重复的组合。

class Solution {
    private List<List<Integer>> res=new ArrayList<>();
    private boolean[] used;
    public List<List<Integer>> combinationSum2(int[] candidates, int target) {
        Arrays.sort(candidates);
        used=new boolean[candidates.length];
        List<Integer> list=new ArrayList<>();
        helper(candidates,0,target,list);
        return res;
    }
    public void helper(int[] nums,int start,int target,List<Integer> list)
    {
        if(target==0)
        {
            res.add(new ArrayList<>(list));
            return ;
        }
        for(int i=start;i<nums.length&&nums[i]<=target;i++)
        {
            if(i>0&&nums[i-1]==nums[i]&&used[i-1]==false)
                continue;
            list.add(nums[i]);
            target-=nums[i];
            used[i]=true;
            helper(nums,i+1,target,list);
            target+=nums[i];
            list.remove(list.size()-1);
            used[i]=false;
        }
        return ;
        
    }
}

216. 组合总和 III

给定一个数组 candidates 和一个目标数 target ,找出 candidates 中所有可以使数字和为 target 的组合。

candidates 中的每个数字在每个组合中只能使用一次。

说明:    所有数字(包括目标数)都是正整数。 解集不能包含重复的组合。

class Solution {
    private List<List<Integer>> res=new ArrayList<>();
    public List<List<Integer>> combinationSum3(int k, int n) {
        if(n>45)
            return res;
        List<Integer> list=new ArrayList<>();
        helper(k,n,1,list);
        return res;
    }
    public void helper(int k,int n,int start,List<Integer> list)
    {
        if(k==0&&n==0)
        {
            res.add(new ArrayList<>(list));
            return ;
        }
        if(k<0||n<0)
            return ;
        for(int i=start;i<=9;i++)
        {
            list.add(i);
            helper(k-1,n-i,i+1,list);
            list.remove(list.size()-1);
        }
        return ;
    }
}

posted @ 2019-08-28 19:35  小路不会迷路  阅读(183)  评论(0编辑  收藏  举报