4.有效括号
- 题目描述
数字 n
代表生成括号的对数,请你设计一个函数,用于能够生成所有可能的并且 有效的 括号组合。
示例 1:
输入:n = 3
输出:["((()))","(()())","(())()","()(())","()()()"]
示例 2:
输入:n = 1
输出:["()"]
- 题目分析
根据实例进行规律探索
n = 1 ()
n = 2 ()() (())
n = 3 ((())) (()()) (())() ()(()) ()()()
一对括号里不包含括号:()()() ()(())
一对括号里包含一对括号:(())()
一对括号里包含两对括号:(()())() ((()))
可以发现这道题目又是符合卡特兰数的规律
1.初始化:
首先,我们定义了一个二维的ArrayList数组dp,其中dp[i]表示有i对括号时的所有可能组合。初始化时,dp[0]包含一个空字符串,因为0对括号只有一种组合,即空字符串。dp[1]包含一个字符串"()",因为1对括号只有一种组合。
2.递推公式:
对于i > 1的情况,我们需要考虑如何从前面的组合生成当前的组合。
假设我们有j对内括号,那么外括号就有i-1-j对。
对于每一对内括号,我们可以从dp[j]中选择一个组合,对于每一对外括号,我们可以从dp[i-1-j]中选择一个组合。
我们将内括号和外括号组合起来,并添加到dp[i]中。这样,我们就得到了所有可能的i对括号的组合。
我们遍历所有可能的j值(从0到i-1),以生成所有可能的组合。
- Java代码实现
public List<String> generateParenthesis(int n) {
//1.创建数组dp[i]:表示节点数为i时的括号类型
ArrayList<String>[] dp = new ArrayList[n + 1];
//2.初始化数组
dp[0] = new ArrayList<>(List.of(""));
dp[1] = new ArrayList<>(List.of("()"));
//3.递推公式
for (int i = 2; i <= n; i++) {
dp[i] = new ArrayList<>();
for (int j = 0; j < i; j++) {
//j:表示内层括号的个数,i-1-j:表示外层括号的个数
for (String s1 : dp[j]) {
for (String s2 : dp[i - 1 - j]) {
dp[i].add("(" + s1 + ")" + s2);
}
}
}
}
return dp[n];
}