图解leetcode77. 组合

1.题目描述:

给定两个整数n和k,返回范围[1,n]中所有可能的k个数的组合。你可以按任何顺序返回答案。

2.回溯算法概述:

①、回溯算法的本质是穷举,穷举所有可能,然后选出我们想要的答案,可以加入剪枝操作提高效率。②、回溯算法解决的问题都可以抽象为树形结构,回溯算法解决的都是在集合中递归查找子集,集合的大小(包括每级递归的子集合)为树的宽度,递归的层数为树的深度。递归存在终止条件,所以抽象树是一棵高度有限的N叉树。③、回溯算法抽象树示意图+代码框架(类似递归三部曲)。上述部分参考代码随想录

 3.代码:

class Solution {
    private List<List<Integer>> resList = new ArrayList<>();
    private List<Integer> list = new ArrayList<>();
    public List<List<Integer>> combine(int n, int k) {
        backTracking(n, k, 0);
        return resList;
    }

    public void backTracking(int n, int k, int index) {//index用来缩小子集
        if (list.size() == k) {
            resList.add(new ArrayList<>(list));//直接add(list)最终全为null,回溯时list会被不断修改,最后add(4)后被remove为null
            return;
        }
        for (int i = index; i < n; i++) {
            list.add(i + 1);
            backTracking(n, k, i + 1);//必须i + 1,不能index + 1
            list.remove(list.size() - 1);//回溯删除上一步递归添加的数据,例如[1,2]还原为[1]在被递归掉用的循环中更新为[1,3]
        }
    }
}

4.剪枝优化:

如果for循环选择的起始位置之后的元素个数小于需要的元素个数(动态变化)则没有必要搜索,在for循环中优化即可。某次回溯中,list集合已有list.size()个元素,则还需要k - list.size()个元素,那么index索引位置后面至少还要有k - list.size()个元素,这里规定了index的上限,反映在代码里也就是n索引的位置,归纳一下有上限为n - (k - list.size()) + 1(索引从0开始)。

class Solution {
    private List<List<Integer>> resList = new ArrayList<>();
    private List<Integer> list = new ArrayList<>();
    public List<List<Integer>> combine(int n, int k) {
        backTracking(n, k, 0);
        return resList;
    }

    public void backTracking(int n, int k, int index) {
        if (list.size() == k) {
            resList.add(new ArrayList<>(list));
            return;
        }
        for (int i = index; i < n - (k - list.size()) + 1; i++) {
            list.add(i + 1);
            backTracking(n, k, i + 1);
            list.remove(list.size() - 1);
        }
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值