Skip to main content

77. 组合 [medium]

77. 组合 [medium]

https://leetcode-cn.com/problems/combinations/

给定两个整数 n 和 k,返回 1 ... n 中所有可能的 k 个数的组合。

示例:

输入: n = 4, k = 2
输出:
[
[2,4],
[3,4],
[2,3],
[1,2],
[1,3],
[1,4],
]

通过次数64,051 | 提交次数86,121

First Try

2020-07-29

经典题目啊,以为全排列能够无脑一波带走,结果这题一出来还是思考了一会儿。

  • 又是backtrack全排列, 特殊点在于不允许[1, 4][4, 1]同时存在
  • 模仿for i in range(0, n - 1): for j in range(i + 1, n)的嵌套写法
  • 官方题解里面只是backtrack(i + 1),并不考虑右边界的问题,虽然是提前剔除无效点实现的效率优化。

排列组合里面,C{N, B}和A{N, B}之间的差别,总算把这个经验补上了。

class Solution:
def combine(self, n: int, k: int) -> List[List[int]]:
# 又是backtrack全排列, 特殊点在于不允许[1, 4]和[4, 1]同时存在
# 模仿`for i in range(0, n - 1): for j in range(i + 1, n)`的嵌套写法
choices = list(range(1, n + 1))
def backtrack(starti, endi, k, seq, rv):
if len(seq) == k:
rv.append(seq[:])
return # 这都忘记写。。
for i in range(starti, endi):
seq.append(choices[i])
# 注意下一个起点是i + 1,而不是starti + 1
backtrack(i + 1, endi + 1, k, seq, rv)
seq.pop()

rv = []
backtrack(0, n - (k - 1), k, [], rv) # 第一个结尾点是 n - (k - 1)而不是n - k
return rv
  • 执行用时:52 ms, 在所有 Python3 提交中击败了92.07%的用户
  • 内存消耗:15 MB, 在所有 Python3 提交中击败了10.53%的用户