Leetcode 22. Generate Parentheses - 生成指定数量的有效圆括号,比如输入2,输出()()(())
Posted 二十六画生的博客
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Leetcode 22. Generate Parentheses - 生成指定数量的有效圆括号,比如输入2,输出()()(())相关的知识,希望对你有一定的参考价值。
Given n
pairs of parentheses, write a function to generate all combinations of well-formed parentheses.
Example 1:
Input: n = 3 Output: ["((()))","(()())","(())()","()(())","()()()"]
Example 2:
Input: n = 1 Output: ["()"]
Constraints:
1 <= n <= 8
https://leetcode.com/problems/generate-parentheses/solution/
看了给定的Solution,方法1、2、3,真是难懂,全是递归.....
自己琢磨出的求解方法,非递归,容易理解很多!
我的方法(本文的方法1): 先设置n=1,保存好();从n=2开始,依赖上次生成的括号字符串,遍历每个括号字符串和其中的每个括号字符,生成本次的括号字符串,再把本次的结果用于计算下次的,如此循环。
字符串拼接:用StringBuilder比"String+A+B+C"的运行时间有所缩短,效率有所提高。
package com.string;
import java.util.*;
/**
* @Author you guess
* @Date 2022/4/10 21:41
* @Version 1.0
* @Desc 生成指定数量的有效圆括号 2->()()、(())
*/
public class Leetcode_22_Generate_Parentheses
/**
* 方法1:优化后
* Runtime: 24 ms, faster than 5.08% of Java online submissions for Generate Parentheses.
* Memory Usage: 45.4 MB, less than 10.08% of Java online submissions for Generate Parentheses.
*
* @param n
* @return
*/
public List<String> generateParenthesis(int n)
List<String> list1 = new ArrayList<>();//存储总的结果
list1.add("()");
if (n == 1)
return list1;
//n=2 3 4 ...
for (int i = 2; i <= n; i++)
Set<String> set = new HashSet<>();//存储当次的结果
for (int j = 0; j < list1.size(); j++)
String s = list1.get(j);
// set.add("()" + s);//左,多余的
// set.add(s + "()");//右,多余的
set.add("(" + s + ")");//外
set.addAll(this.addParenthesis(s));
list1 = new ArrayList<>(set);
return list1;
/**
* 优化后
*/
public Set<String> addParenthesis(String s)
Set<String> set = new HashSet<>();
Stack<Integer> stack = new Stack<>();
for (int i = 0; i < s.length(); i++)
StringBuilder sb = new StringBuilder();
char c = s.charAt(i);
if (c == '(')
//()()(()) -> (()())(()),这个比较容易忘记!!
if (stack.isEmpty())
sb.append("(").append(s, 0, i).append(")").append(s.substring(i));
set.add(sb.toString());
//set.add("(" + s.substring(0, i) + ")" + s.substring(i));
stack.push(i);
else
int left = stack.pop();
int right = i;
//在里面加一层(),比如([待加入])() -> ([()])()
sb.append(s, 0, left + 1).append("(").append(s, left + 1, right).append(")").append(s.substring(right));
set.add(sb.toString());
//set.add(s.substring(0, left + 1) + "(" + s.substring(left + 1, right) + ")" + s.substring(right));
return set;
class Entry
Character c;
Integer index;
public Entry(Character c, Integer index)
this.c = c;
this.index = index;
/**
* 这个也正确,不过不必使用Entry类
* 未优化
*
* @param s
* @return
*/
public Set<String> addParenthesisUseEntry(String s)
Set<String> set = new HashSet<>();
Stack<Entry> stack = new Stack<>();
for (int i = 0; i < s.length(); i++)
char c = s.charAt(i);
if (c == '(')
//()()(()) -> (()())(()),这个比较容易忘记!!
if (stack.isEmpty())
set.add("(" + s.substring(0, i) + ")" + s.substring(i));
Entry leftEntry = new Entry(s.charAt(i), i);
stack.push(leftEntry);
else
Entry leftEntry = stack.pop();
int left = leftEntry.index;// int left = leftEntry.getIndex() ; 同义
int right = i;
set.add(s.substring(0, left + 1) + "(" + s.substring(left + 1, right) + ")" + s.substring(right));
return set;
/**
* Wrong Answer
* <p>
* Input
* 4
* Output
* ["()()()()","(()()())","()(()())","(()())()","((()()))","()()(())","()(())()","(()(()))","()(())()","(())()()","((())())","()((()))","((()))()","(((())))"]
* Expected
* ["(((())))","((()()))","((())())","((()))()","(()(()))","(()()())","(()())()","(())(())","(())()()","()((()))","()(()())","()(())()","()()(())","()()()()"]
* <p>
* 结果:
* 缺少"(())(())"
* 输出了2个"()(())()"
*
* @param n
* @return
*/
public List<String> generateParenthesisWrong(int n)
List<String> list1 = new ArrayList<>();
list1.add("()");
if (n == 1)
return list1;
//n=2 3 4 ...
for (int i = 2; i <= n; i++)
List<String> list2 = new ArrayList<>();
for (int j = 0; j < list1.size(); j++)
if (j == 0)
list2.add(list1.get(j) + "()");//右
list2.add("(" + list1.get(j) + ")");//外
else
list2.add("()" + list1.get(j));//左
list2.add(list1.get(j) + "()");//右
list2.add("(" + list1.get(j) + ")");//外
list1 = list2;
return list1;
/**
* Wrong Answer
* 6
* Output
* [()(()())(()), ()((()))()(), ()(((())))(), (()((())))(), ((()()(()))), ()(())(())(), (()(()))()(), (()())(())(), ((())(()))(), (((())())()), ((()))()()(), ()((())())(), (((()())())), (()(())())(), ((()(())))(), (()()()()()), ((()))(())(), (()(()(()))), (())()(()()), ()(()(()())), ()()()()()(), ()((()())()), (()()(()))(), (((()))())(), ((()()()())), ()(())()()(), (())((()))(), ((()())())(), (())(()(())), (()(())()()), ((((()))())), (((())(()))), (()((())())), (()()()(())), ()()(())(()), (()())((())), ((((()())))), ()()()(())(), (())()(())(), (()(((())))), (((()()()))), ()()((())()), ()(((()()))), ((())()(())), (()(()()())), ()((()()())), ((()())()()), ()((())(())), ((())((()))), ()(()())()(), ()(((()))()), ((())())(()), ((()(())())), ((()()))()(), ()(())(()()), ()((()(()))), ((()))((())), ()(()()()()), (()()(())()), ((())(())()), ((()((())))), ()(()(()))(), (((()))(())), ()()(()(())), ((()()()))(), (())((()())), (()()())(()), (())(()())(), (((((()))))), (())()()()(), ()()(((()))), ((((()))))(), (((())))(()), (((()()))()), ((())())()(), (()()()())(), (())(((()))), ()()()((())), ()(()(())()), (())()((())), ()(())()(()), ((())()())(), (()(()()))(), ()((()()))(), (()())()(()), (())(()()()), ()((()))(()), (()((()()))), (()()())()(), (())(())()(), (((())()())), ((()))()(()), ((()(()()))), ()(()()())(), ()()((()())), ()()(()())(), (()()((()))), ((()(()))()), ()(((())())), ((()()))(()), ((()))(()()), ()(())((())), ((())()()()), (())(())(()), ()((((())))), ((())(()())), ((()()())()), ()()()()(()), ((((())()))), (())((())()), ()()(()()()), (()((()))()), (())()()(()), (((()())))(), (()(())(())), ()()(())()(), (((())))()(), ((((())))()), (((()))()()), (((()(())))), ()()()(()()), (()(()))(()), (((())()))(), (()()(()())), ()(()()(())), ()()((()))(), (()(()())()), ()((())()()), ((()())(())), (()())()()(), ()(()((())))]
* Expected
* [(())()(())()(), (())(((()))()), (())((()(()))), (())((()))(()), (())()()(()()), (())(()(()))(), (())()(()()()), (())(()(()())), (())()((()))(), (())()((()())), (())(()()()()), (())(((()()))), (())()()()()(), (())((()())()), (())(())()()(), (())()(()())(), (())(()(())()), (())()(()(())), (())(((())))(), (())(((())())), (())(()())(()), (())()(((()))), (())(()((()))), (())(())(())(), (())(())((())), (())()(())(()), (())()()(())(), (())()()((())), (())((()))()(), (())((())()()), (())((((())))), (())((()()())), (())(()()())(), (())(()()(())), (())()((())()), (())(())()(()), (())((()()))(), (())((())())(), (())()()()(()), (())((())(())), (())(())(()()), (())(()())()(), (())()()()(), (())(()())(), (())(()(())), (())()()(()), (())(())()(), (())(((()))), (())(())(()), (())()((())), (())()(())(), (())()(()()), (())(()()()), (())((()())), (())((()))(), (())((())()), (()())()()(), (()())(()()), (()())()(()), (()())(())(), (()())((())), ((()))()()(), ((()))(()()), ((()))()(()), ((()))(())(), ((()))((())), (()()())()(), (()()())(()), ((()()))()(), ((()()))(()), (()(()))()(), (()(()))(()), ((())())()(), ((())())(()), (((())))()(), (((())))(()), (()()()())(), ((()())())(), ((()(())))(), (()()(()))(), ((())()())(), ((((()))))(), ((())(()))(), (()((())))(), (()(())())(), (()(()()))(), ((()()()))(), (((()())))(), (((()))())(), (((())()))(), (()(())()())(), ((((()))()))(), (((()(()))))(), (((()))(()))(), (()()(()()))(), ((()(()))())(), (()(()()()))(), ((()(()())))(), (()((()))())(), (()((()())))(), ((()()()()))(), ((((()()))))(), (()()()()())(), (((()())()))(), ((())()()())(), (()(()())())(), ((()(())()))(), (()(()(())))(), ((((())))())(), ((((())())))(), ((()())(()))(), (()(((()))))(), ((()((()))))(), ((())(())())(), ((())((())))(), (()(())(()))(), (()()(())())(), (()()((())))(), (((()))()())(), (((())()()))(), (((((())))))(), (((()()())))(), ((()()())())(), ((()()(())))(), (()((())()))(), ((())()(()))(), (((()()))())(), (((())())())(), (()()()(()))(), (((())(())))(), ((())(()()))(), ((()())()())()]
* <p>
* 缺少"(()())(()())"
*
* @param n
* @return
*/
public List<String> generateParenthesisWrong2(int n)
List<String> list1 = new ArrayList<>();
list1.add("()");
if (n == 1)
return list1;
//n=2 3 4 ...
for (int i = 2; i <= n; i++)
Set<String> set = new HashSet<>();
for (int j = 0; j < list1.size(); j++)
String s1 = list1.get(j);
set.add("()" + s1);//左
set.add(s1 + "()");//右
set.add("(" + s1 + ")");//外
if (s1.charAt(0) == '(' && s1.charAt(s1.length() - 1) == ')')
set.add("(" + s1 + ")");//外
for (int k = 0; k < s1.length() - 1; k++)
if (s1.charAt(k) == '(' && s1.charAt(k + 1) == ')')
set.add(s1.substring(0, k + 1) + "()" + s1.substring(k + 1));//内部
list1 = new ArrayList<>(set);
return list1;
public static void main(String[] args)
Leetcode_22_Generate_Parentheses main = new Leetcode_22_Generate_Parentheses();
//System.out.println(main.generateParenthesis(3));
System.out.println(main.generateParenthesisSolution(3));
/**
* 方法2:Approach 2: Backtracking
* Runtime: 2 ms, faster than 65.13% of Java online submissions for Generate Parentheses.
* Memory Usage: 43.1 MB, less than 78.53% of Java online submissions for Generate Parentheses.
*
* @param n
* @return
*/
public List<String> generateParenthesisSolution(int n)
List<String> ans = new ArrayList();
backtrack(ans, new StringBuilder(), 0, 0, n);
return ans;
public void backtrack(List<String> ans, StringBuilder cur, int open, int close, int max)
if (cur.length() == max * 2)
ans.add(cur.toString());
return;
if (open < max)
cur.append("(");
backtrack(ans, cur, open + 1, close, max);
cur.deleteCharAt(cur.length() - 1);
if (close < open)
cur.append(")");
backtrack(ans, cur, open, close + 1, max);
cur.deleteCharAt(cur.length() - 1);
/**
* 方法3:Approach 3: Closure Number
* Runtime: 7 ms, faster than 16.99% of Java online submissions for Generate Parentheses.
* Memory Usage: 42.2 MB, less than 91.80% of Java online submissions for Generate Parentheses.
*
* @param n
* @return
*/
public List<String> generateParenthesisSolution3(int n)
List<String> ans = new ArrayList();
if (n == 0)
ans.add("");
else
for (int c = 0; c < n; ++c)
for (String left : generateParenthesisSolution(c))
for (String right : generateParenthesisSolution(n - 1 - c))
ans.add("(" + left + ")" + right);
return ans;
以上是关于Leetcode 22. Generate Parentheses - 生成指定数量的有效圆括号,比如输入2,输出()()(())的主要内容,如果未能解决你的问题,请参考以下文章
Leetcode 22. Generate Parentheses
leetcode22. Generate Parentheses
leetcode 22 -- Generate Parentheses
[leetcode-22-Generate Parentheses]