题目
题目描述
数字 n 代表生成括号的对数,请你设计一个函数,用于能够生成所有可能的并且 有效的 括号组合。
示例 1:
输入:n = 3
输出:[“((()))”,“(()())”,“(())()”,“()(())”,“()()()”]
示例 2:
输入:n = 1
输出:[“()”]
提示:
1 <= n <= 8
题目链接
题解
题目要求设计一个函数,该函数接收一个正整数 n 作为参数,并返回所有可能的、有效的括号组合。每个组合由 n 对括号组成,即共有 2n 个字符,其中包含 n 个左括号 ‘(’ 和 n 个右括号 ‘)’。有效括号组合意味着每一个右括号都有一个对应的左括号与之匹配,并且在任意位置上,左括号的数量都不小于右括号的数量。
解题思路
一种常见的解法是使用回溯算法(Backtracking),它是一种通过构建所有可能的选择来解决问题的方法,同时在发现当前路径不可能产生解决方案时立即停止探索这条路径的技术,这被称为“剪枝”。对于本题而言,我们可以将问题看作是在构建一棵二叉树,其中每个节点代表一个决策点:是否添加一个左括号或右括号。
回溯算法的具体步骤如下:
- 初始化:创建一个空的结果列表
res
来保存所有的有效括号组合。 - 递归终止条件:当已经添加了 n 个左括号和 n 个右括号时,说明找到了一个完整的有效括号组合,将其加入结果列表中。
- 选择分支:
- 如果当前字符串中的左括号数量小于 n,则可以继续添加左括号。
- 如果当前字符串中的右括号数量小于左括号数量,则可以继续添加右括号。
- 回溯:每完成一次递归调用后,需要撤销之前的选择以尝试其他可能性。
- 优化:为了避免不必要的计算,在某些情况下可以直接返回而不进行进一步的递归。例如,如果剩余可用的右括号数量超过了左括号数量,则没有必要继续生成这个序列。
示例代码
以下是 Python 实现的一个例子:
def generateParenthesis(n):
def backtrack(s='', left=0, right=0):
if len(s) == 2 * n:
res.append(s)
return
if left < n:
backtrack(s+'(', left+1, right)
if right < left:
backtrack(s+')', left, right+1)
res = []
backtrack()
return res
这段代码定义了一个名为 generateParenthesis
的函数,它接受一个整数 n 作为输入,并返回一个包含所有有效括号组合的列表。内部定义了一个辅助函数 backtrack
,用于递归地构建括号组合。backtrack
函数接收三个参数:当前构建的部分字符串 s
,以及两个计数器 left
和 right
分别记录已使用的左括号和右括号的数量。每当构建出一个完整的括号组合时,就将其添加到结果列表 res
中。
此外,还有其他几种方法也可以用来解决这个问题,比如动态规划或者直接利用数学公式(如卡特兰数)来生成所有可能的有效括号组合。但这些方法通常更为复杂,而且回溯算法在这个问题上表现得非常直观且易于理解。
综上所述,回溯算法提供了一种简单而有效的方式来生成所有可能的有效括号组合。通过控制左右括号的数量并适时地应用剪枝技术,我们可以高效地找到所有满足条件的答案。对于给定的例子,当 n=3 时,输出将是 ["((()))","(()())","(())()","()(())","()()()"]
;而对于 n=1,则输出为 ["()"]
。这种方法不仅适用于较小的 n 值,而且对于较大的 n 值也能保持良好的性能。