Given n pairs of parentheses, write a function to generate all combinations of well-formed parentheses.

For example, given n = 3, a solution set is:

  1. [
  2. "((()))",
  3. "(()())",
  4. "(())()",
  5. "()(())",
  6. "()()()"
  7. ]
  

在 LeetCode 中有关括号的题共有七道,除了这一道的另外六道是 Score of ParenthesesValid Parenthesis String, Remove Invalid ParenthesesDifferent Ways to Add ParenthesesValid Parentheses 和 Longest Valid Parentheses。这道题给定一个数字n,让生成共有n个括号的所有正确的形式,对于这种列出所有结果的题首先还是考虑用递归 Recursion 来解,由于字符串只有左括号和右括号两种字符,而且最终结果必定是左括号3个,右括号3个,所以这里定义两个变量 left 和 right 分别表示剩余左右括号的个数,如果在某次递归时,左括号的个数大于右括号的个数,说明此时生成的字符串中右括号的个数大于左括号的个数,即会出现 ')(' 这样的非法串,所以这种情况直接返回,不继续处理。如果 left 和 right 都为0,则说明此时生成的字符串已有3个左括号和3个右括号,且字符串合法,则存入结果中后返回。如果以上两种情况都不满足,若此时 left 大于0,则调用递归函数,注意参数的更新,若 right 大于0,则调用递归函数,同样要更新参数,参见代码如下:

C++ 解法一:

  1. class Solution {
  2. public:
  3. vector<string> generateParenthesis(int n) {
  4. vector<string> res;
  5. generateParenthesisDFS(n, n, "", res);
  6. return res;
  7. }
  8. void generateParenthesisDFS(int left, int right, string out, vector<string> &res) {
  9. if (left > right) return;
  10. if (left == && right == ) res.push_back(out);
  11. else {
  12. if (left > ) generateParenthesisDFS(left - , right, out + '(', res);
  13. if (right > ) generateParenthesisDFS(left, right - , out + ')', res);
  14. }
  15. }
  16. };

Java 解法一:

  1. public class Solution {
  2. public List<String> generateParenthesis(int n) {
  3. List<String> res = new ArrayList<String>();
  4. helper(n, n, "", res);
  5. return res;
  6. }
  7. void helper(int left, int right, String out, List<String> res) {
  8. if (left < 0 || right < 0 || left > right) return;
  9. if (left == 0 && right == 0) {
  10. res.add(out);
  11. return;
  12. }
  13. helper(left - 1, right, out + "(", res);
  14. helper(left, right - 1, out + ")", res);
  15. }
  16. }

再来看那一种方法,这种方法是 CareerCup 书上给的方法,感觉也是满巧妙的一种方法,这种方法的思想是找左括号,每找到一个左括号,就在其后面加一个完整的括号,最后再在开头加一个 (),就形成了所有的情况,需要注意的是,有时候会出现重复的情况,所以用set数据结构,好处是如果遇到重复项,不会加入到结果中,最后我们再把set转为vector即可,参见代码如下::

n=1:    ()

n=2:    (())    ()()

n=3:    (()())    ((()))    ()(())    (())()    ()()()

C++ 解法二:

  1. class Solution {
  2. public:
  3. vector<string> generateParenthesis(int n) {
  4. unordered_set<string> st;
  5. if (n == ) st.insert("");
  6. else {
  7. vector<string> pre = generateParenthesis(n - );
  8. for (auto a : pre) {
  9. for (int i = ; i < a.size(); ++i) {
  10. if (a[i] == '(') {
  11. a.insert(a.begin() + i + , '(');
  12. a.insert(a.begin() + i + , ')');
  13. st.insert(a);
  14. a.erase(a.begin() + i + , a.begin() + i + );
  15. }
  16. }
  17. st.insert("()" + a);
  18. }
  19. }
  20. return vector<string>(st.begin(), st.end());
  21. }
  22. };

Java 解法二:

  1. public class Solution {
  2. public List<String> generateParenthesis(int n) {
  3. Set<String> res = new HashSet<String>();
  4. if (n == 0) {
  5. res.add("");
  6. } else {
  7. List<String> pre = generateParenthesis(n - 1);
  8. for (String str : pre) {
  9. for (int i = 0; i < str.length(); ++i) {
  10. if (str.charAt(i) == '(') {
  11. str = str.substring(0, i + 1) + "()" + str.substring(i + 1, str.length());
  12. res.add(str);
  13. str = str.substring(0, i + 1) + str.substring(i + 3, str.length());
  14. }
  15. }
  16. res.add("()" + str);
  17. }
  18. }
  19. return new ArrayList(res);
  20. }
  21. }

Github 同步地址:

https://github.com/grandyang/leetcode/issues/22

类似题目:

Remove Invalid Parentheses

Different Ways to Add Parentheses

Longest Valid Parentheses

Valid Parentheses

Score of Parentheses

Valid Parenthesis String

参考资料:

https://leetcode.com/problems/generate-parentheses/

https://leetcode.com/problems/generate-parentheses/discuss/10127/An-iterative-method.

https://leetcode.com/problems/generate-parentheses/discuss/10337/My-accepted-JAVA-solution

https://leetcode.com/problems/generate-parentheses/discuss/10105/Concise-recursive-C%2B%2B-solution

LeetCode All in One 题目讲解汇总(持续更新中...)

[LeetCode] Generate Parentheses 生成括号的更多相关文章

  1. [CareerCup] 9.6 Generate Parentheses 生成括号

    9.6 Implement an algorithm to print all valid (e.g., properly opened and closed) combinations of n-p ...

  2. generate parentheses(生成括号)

    Given n pairs of parentheses, write a function to generate all combinations of well-formed parenthes ...

  3. [LintCode] Generate Parentheses 生成括号

    Given n pairs of parentheses, write a function to generate all combinations of well-formed parenthes ...

  4. [LeetCode] 22. Generate Parentheses 生成括号

    Given n pairs of parentheses, write a function to generate all combinations of well-formed parenthes ...

  5. [leetcode]22. Generate Parentheses生成括号

    Given n pairs of parentheses, write a function to generate all combinations of well-formed parenthes ...

  6. 022 Generate Parentheses 生成括号

    给 n 对括号,写一个函数生成所有合适的括号组合.比如,给定 n = 3,一个结果为:[  "((()))",  "(()())",  "(())() ...

  7. LeetCode Generate Parentheses 构造括号串(DFS简单题)

    题意: 产生n对合法括号的所有组合,用vector<string>返回. 思路: 递归和迭代都可以产生.复杂度都可以为O(2n*合法的括号组合数),即每次产生出的括号序列都保证是合法的. ...

  8. 22.Generate Parentheses[M]括号生成

    题目 Given n pairs of parentheses, write a function to generate all combinations of well-formed parent ...

  9. [LeetCode] Valid Parentheses 验证括号

    Given a string containing just the characters '(', ')', '{', '}', '[' and ']', determine if the inpu ...

随机推荐

  1. 【知识积累】try-catch-finally+return总结

    一.前言 对于找Java相关工作的读者而言,在笔试中肯定免不了遇到try-catch-finally + return的题型,需要面试这清楚返回值,这也是这篇博文产生的由来.本文将从字节码层面来解释为 ...

  2. 由浅入深学习ajax跨域(JSONP)问题

    什么是跨域?说直白点就是获取别人网站上的内容.但这么说貌似又有点混淆,因为通常我们用ajax+php就可以获取别人网站的内容,来看下面这个例子. 来看看跨域的例子,jquery+ajax是不能跨域请求 ...

  3. 基于 HTML5 的 Web SCADA 报表

    背景 最近在一个 SCADA 项目中遇到了在 Web 页面中展示设备报表的需求.一个完整的报表,一般包含了筛选操作区.表格.Chart.展板等多种元素,而其中的数据表格是最常用的控件.在以往的工业项目 ...

  4. iOS 触摸事件与UIResponder(内容根据iOS编程编写)

    触摸事件 因为 UIView 是 UIResponder 的子类,所以覆盖以下四个方法就可以处理四种不同的触摸事件: 1.  一根手指或多根手指触摸屏幕 - (void)touchesBegan:(N ...

  5. 关于Java泛型的使用

    在目前我遇到的java项目中,泛型应用的最多的就属集合了.当要从数据库取出多个对象或者说是多条记录时,往往都要使用集合,那么为什么这么使用,或者使用时有什么要注意的地方,请关注以下内容. 感谢Wind ...

  6. jQuery Raty 星级评分

    在线实例 实例演示 使用方法 <div id="star"></div> 复制 $('#star').raty(); 复制 你只需要有一个 div构建Rat ...

  7. JS中的对象

    什么事对象?对象是一个整体,对外提供一些操作.而面向对象,就是使用对象时,只关注对象提供的功能,不关注内部的细节,面向对象是一种通用思想. 面向对象编程的特点: 抽象:抓住核心问题: 封装:不考虑内部 ...

  8. jQuery css3仿游戏网站右键环形菜单

    效果展示 http://hovertree.com/texiao/jquery/86/ PC用户右键弹出环形菜单. 手机用户扫描二维码: 长安可以弹出环形菜单. 转自:http://hovertree ...

  9. AccountName LoginName 变更

    当AD中把AccountName改掉后,网站集不会自动同步LoginName,需要使用命令行Move-SPUser domain/A->domian/B /*2013 Claim 认证  必须加 ...

  10. Scala 包

    包的绝对地址_root_.开始 如_root_.scala.collection.mutable.ArrayBuffer