问题地址:LeetCode 77.组合
1.问题思路
从n个数内,选择k个数出来,这是一个典型的组合问题。面对组合问题可以使用回溯算法。对于回溯递归可以使用递归三部曲。
-
确认递归方法参数及返回值
public void recursion(List<List> result, List item, int start, int n, int k) ;result用来接收所有可能的结果。因为这里1~n内的数不能重复选取,这里使用start记录当前的数,每层的广度遍历为[start, n]。 -
终止条件
当前已经选择列表数=k时,进行退出。 -
广度遍历区间处理
广度优先遍历区间为【start, n】,再进行下一层遍历前,需要将start+=1。下一层遍历结束后进行回溯start-=1。
2.代码实现
class Solution {
public List<List<Integer>> combine(int n, int k) {
// 存储组合
List<List<Integer>> result = new ArrayList<>();
dfs(result, new ArrayList<>(), 1, n, k);
return result;
}
public void dfs(List<List<Integer>> result, List<Integer> item, int start, int n, int k) {
// end
if (item.size() == k) {
// 因为List是引用类型,需要重新new一个。不然会影响之前的结果
result.add(new ArrayList<>(item));
return;
}
// bfs
for (int i = start; i <= n; i++) {
item.add(i);
// 垂直递归
recursion(result, item, i + 1, n, k);
// 回溯
item.remove(item.size()-1);
}
}
}