Merge branch 'youngyangyang04:master' into master
This commit is contained in:
@@ -29,7 +29,7 @@
|
||||
|
||||
也可以直接看我的B站视频:[带你学透回溯算法-组合问题(对应力扣题目:77.组合)](https://www.bilibili.com/video/BV1ti4y1L7cv#reply3733925949)
|
||||
|
||||
## 思路
|
||||
# 思路
|
||||
|
||||
|
||||
本题这是回溯法的经典题目。
|
||||
@@ -37,7 +37,7 @@
|
||||
直接的解法当然是使用for循环,例如示例中k为2,很容易想到 用两个for循环,这样就可以输出 和示例中一样的结果。
|
||||
|
||||
代码如下:
|
||||
```
|
||||
```CPP
|
||||
int n = 4;
|
||||
for (int i = 1; i <= n; i++) {
|
||||
for (int j = i + 1; j <= n; j++) {
|
||||
@@ -49,7 +49,7 @@ for (int i = 1; i <= n; i++) {
|
||||
输入:n = 100, k = 3
|
||||
那么就三层for循环,代码如下:
|
||||
|
||||
```
|
||||
```CPP
|
||||
int n = 100;
|
||||
for (int i = 1; i <= n; i++) {
|
||||
for (int j = i + 1; j <= n; j++) {
|
||||
@@ -301,7 +301,7 @@ for (int i = startIndex; i <= n - (k - path.size()) + 1; i++) // i为本次搜
|
||||
|
||||
优化后整体代码如下:
|
||||
|
||||
```
|
||||
```CPP
|
||||
class Solution {
|
||||
private:
|
||||
vector<vector<int>> result;
|
||||
@@ -336,10 +336,10 @@ public:
|
||||
|
||||
|
||||
|
||||
## 其他语言版本
|
||||
# 其他语言版本
|
||||
|
||||
|
||||
Java:
|
||||
## Java:
|
||||
```java
|
||||
class Solution {
|
||||
List<List<Integer>> result = new ArrayList<>();
|
||||
@@ -397,7 +397,25 @@ class Solution(object):
|
||||
return result
|
||||
```
|
||||
|
||||
Python:
|
||||
## Python
|
||||
```python
|
||||
class Solution:
|
||||
def combine(self, n: int, k: int) -> List[List[int]]:
|
||||
res = []
|
||||
path = []
|
||||
def backtrack(n, k, StartIndex):
|
||||
if len(path) == k:
|
||||
res.append(path[:])
|
||||
return
|
||||
for i in range(StartIndex, n-(k-len(path)) + 2):
|
||||
path.append(i)
|
||||
backtrack(n, k, i+1)
|
||||
path.pop()
|
||||
backtrack(n, k, 1)
|
||||
return res
|
||||
```
|
||||
|
||||
剪枝:
|
||||
```python3
|
||||
class Solution:
|
||||
def combine(self, n: int, k: int) -> List[List[int]]:
|
||||
@@ -406,15 +424,19 @@ class Solution:
|
||||
def backtrack(n,k,startIndex):
|
||||
if len(path) == k:
|
||||
res.append(path[:])
|
||||
return
|
||||
for i in range(startIndex,n+1):
|
||||
return
|
||||
for i in range(startIndex,n-(k-len(path))+2): #优化的地方
|
||||
path.append(i) #处理节点
|
||||
backtrack(n,k,i+1) #递归
|
||||
path.pop() #回溯,撤销处理的节点
|
||||
backtrack(n,k,1)
|
||||
return res
|
||||
backtrack(n,k,1)
|
||||
return res
|
||||
```
|
||||
javascript
|
||||
|
||||
|
||||
## javascript
|
||||
|
||||
剪枝:
|
||||
```javascript
|
||||
let result = []
|
||||
let path = []
|
||||
@@ -434,8 +456,11 @@ const combineHelper = (n, k, startIndex) => {
|
||||
path.pop()
|
||||
}
|
||||
}
|
||||
```
|
||||
Go:
|
||||
```
|
||||
|
||||
|
||||
|
||||
## Go
|
||||
```Go
|
||||
var res [][]int
|
||||
func combine(n int, k int) [][]int {
|
||||
@@ -462,8 +487,35 @@ func backtrack(n,k,start int,track []int){
|
||||
}
|
||||
}
|
||||
```
|
||||
剪枝:
|
||||
```Go
|
||||
var res [][]int
|
||||
func combine(n int, k int) [][]int {
|
||||
res=[][]int{}
|
||||
if n <= 0 || k <= 0 || k > n {
|
||||
return res
|
||||
}
|
||||
backtrack(n, k, 1, []int{})
|
||||
return res
|
||||
}
|
||||
func backtrack(n,k,start int,track []int){
|
||||
if len(track)==k{
|
||||
temp:=make([]int,k)
|
||||
copy(temp,track)
|
||||
res=append(res,temp)
|
||||
}
|
||||
if len(track)+n-start+1 < k {
|
||||
return
|
||||
}
|
||||
for i:=start;i<=n;i++{
|
||||
track=append(track,i)
|
||||
backtrack(n,k,i+1,track)
|
||||
track=track[:len(track)-1]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
C:
|
||||
## C
|
||||
```c
|
||||
int* path;
|
||||
int pathTop;
|
||||
@@ -517,6 +569,60 @@ int** combine(int n, int k, int* returnSize, int** returnColumnSizes){
|
||||
}
|
||||
```
|
||||
|
||||
剪枝:
|
||||
```c
|
||||
int* path;
|
||||
int pathTop;
|
||||
int** ans;
|
||||
int ansTop;
|
||||
|
||||
void backtracking(int n, int k,int startIndex) {
|
||||
//当path中元素个数为k个时,我们需要将path数组放入ans二维数组中
|
||||
if(pathTop == k) {
|
||||
//path数组为我们动态申请,若直接将其地址放入二维数组,path数组中的值会随着我们回溯而逐渐变化
|
||||
//因此创建新的数组存储path中的值
|
||||
int* temp = (int*)malloc(sizeof(int) * k);
|
||||
int i;
|
||||
for(i = 0; i < k; i++) {
|
||||
temp[i] = path[i];
|
||||
}
|
||||
ans[ansTop++] = temp;
|
||||
return ;
|
||||
}
|
||||
|
||||
int j;
|
||||
for(j = startIndex; j <= n- (k - pathTop) + 1;j++) {
|
||||
//将当前结点放入path数组
|
||||
path[pathTop++] = j;
|
||||
//进行递归
|
||||
backtracking(n, k, j + 1);
|
||||
//进行回溯,将数组最上层结点弹出
|
||||
pathTop--;
|
||||
}
|
||||
}
|
||||
|
||||
int** combine(int n, int k, int* returnSize, int** returnColumnSizes){
|
||||
//path数组存储符合条件的结果
|
||||
path = (int*)malloc(sizeof(int) * k);
|
||||
//ans二维数组存储符合条件的结果数组的集合。(数组足够大,避免极端情况)
|
||||
ans = (int**)malloc(sizeof(int*) * 10000);
|
||||
pathTop = ansTop = 0;
|
||||
|
||||
//回溯算法
|
||||
backtracking(n, k, 1);
|
||||
//最后的返回大小为ans数组大小
|
||||
*returnSize = ansTop;
|
||||
//returnColumnSizes数组存储ans二维数组对应下标中一维数组的长度(都为k)
|
||||
*returnColumnSizes = (int*)malloc(sizeof(int) *(*returnSize));
|
||||
int i;
|
||||
for(i = 0; i < *returnSize; i++) {
|
||||
(*returnColumnSizes)[i] = k;
|
||||
}
|
||||
//返回ans二维数组
|
||||
return ans;
|
||||
}
|
||||
```
|
||||
|
||||
-----------------------
|
||||
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)
|
||||
* B站视频:[代码随想录](https://space.bilibili.com/525438321)
|
||||
|
||||
Reference in New Issue
Block a user