0216.-组合总和 III


找出所有相加之和为 n 的 k 个数的组合。组合中只允许含有 1 - 9 的正整数,并且每种组合中不存在重复的数字。

说明:

所有数字都是正整数。
解集不能包含重复的组合。 
示例 1:

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

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

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/combination-sum-iii

参考:

  • https://leetcode-cn.com/problems/combination-sum-iii/solution/dai-ma-sui-xiang-lu-dai-ni-xue-tou-hui-s-petp/

python

# 0216.组合总和III

class Solution:
    def combinationSum3(self, k: int, n: int) -> [[int]]:
        res = []
        path = []

        def findFinalPath(n,k,sum,startIndex):
            if sum > n:
                return # 剪枝操作
            if sum == n and len(path) == k:
                return res.append(path[:])
            # 不剪枝的for loop
            # for i in range(startIndex, 10):
            for i in range(startIndex, 9-(k-len(path))+2):
                path.append(i)
                sum += i
                findFinalPath(n,k,sum,i+1) # 调整startIndex
                sum -= i
                path.pop()

        findFinalPath(n,k,0,1)
        return res

golang

package backTrack


// 回溯
func combinationSum3(k,n int) [][]int {
	var path []int
	var res [][]int
	backTrackSum3(n,k,1,&path,&res)
	return res
}

func backTrackSum3(n,k,startIndex int, path *[]int, res *[][]int)  {
	// 递归终止条件
	if len(*path) == k {
		var sum int
		tmp := make([]int, k)
		for k,v := range *path {
			sum += v
			tmp[k] = v
		}
		if sum == n {
			*res = append(*res, tmp)
		}
		return // 即使 len==k, 但sum!=n也return跳出
	}
	// i < 9-(k-len(*path))+1做了剪枝,(k-len(*track)表示还剩多少个可填充的元素),不剪枝则 i < 10(1-9)
	for i:=startIndex;i<=9-(k-len(*path))+1;i++ {
		// 记录path
		*path = append(*path, i)
		// 递归
		backTrackSum3(n,k,i+1,path,res)
		// 回溯
		*path = (*path)[:len(*path)-1]
	}
}