问题:

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:

[

"((()))",

"(()())",

"(())()",

"()(())",

"()()()"

]

官方难度:

Medium

翻译:

合并n个括号,生成所有n个括号组成的合理序列。

例子:

给定n=3,解集为

[

"((()))",

"(()())",

"(())()",

"()(())",

"()()()"

]

方法一:

  1. 初始的思想,考虑使用递归,每次优先获取n-1个括号所有情况下的集合,然后插入新的括号。
  2. 递归的终点是n=1,返回包含一个元素“()”的集合。
  3. 每次先加“(”,在第一个位置和一个“)”的下一个位置,插入左括号。
  4. 然后加右括号,从加入的左括号开始,统计左括号和右括号的个数,在左括号个数大于右括号个数的情况下,才可以加入右括号。
  5. 不难发现,虽然已经极力避免了,但是这种方法会出现很多的重复情况,所以需要一个Set集合去重,在递归结束之后,转化成List集合返回。

方法一的解题代码:

     // 根据n-1的情况增加括号
public static List<String> method(int n) {
List<String> list = new ArrayList<>(getPharentheses(n));
return list;
} private static Set<String> getPharentheses(int n) {
Set<String> set = new HashSet<>();
if (n == 1) {
set.add("()");
} else {
Set<String> last = getPharentheses(n - 1);
for (String s : last) {
String s1 = "(" + s;
int l1 = 0;
int r1 = 0;
for (int j = 1; j < s1.length(); j++) {
if (s1.charAt(j) == '(') {
l1++;
} else {
r1++;
}
// 这里有重复的可能性
if (l1 > r1) {
set.add(s1.substring(0, j + 1) + ")" + s1.substring(j + 1));
}
}
// 先加左括号
for (int i = 1; i < s.length(); i++) {
if (s.charAt(i) == ')') {
String str = s.substring(0, i + 1) + "(" + s.substring(i + 1);
// 左右括号计数
int l = 0;
int r = 0;
for (int j = i + 1; j < str.length(); j++) {
if (str.charAt(j) == '(') {
l++;
} else {
r++;
}
// 这里有重复的可能性
if (l > r) {
set.add(str.substring(0, j + 1) + ")" + str.substring(j + 1));
}
}
}
}
}
}
return set;
}

method

方法二:

  1. 显而易见,如果通过某种算法,没有重复的情况产生,那么方法的执行效率一定会快很多。
  2. 假设n=3。先加上所有的左括号,“(((”,那么右括号的可能性只有一个,那就是“((()))”。
  3. 然后回退一步,少加一个左括号,加上一个右括号,之后再加上这个左括号,会形成以下形式“(()())”。
  4. 后加的左括号再回退一步“(())()”。依次类推,直到这个左括号不能再加为止,回退至第一步,在一开始回退2个左括号,得到以下2种形式“()(())”和“()()()”。
  5. 发现回退的左括号为n时,结束。
  6. 解题的代码形式很简单,但是逻辑比较难捋通顺。
  7. 注意入参检查。

方法二的解题代码:

     public static List<String> generateParenthesis(int n) {
if (n < 1) {
throw new IllegalArgumentException("Input error");
}
List<String> list = new ArrayList<>();
generate(n, n, "", list);
return list;
} // 先加所有左括号,遍历所有可能性,然后回退一个左括号,依次类推
private static void generate(int left, int right, String current, List<String> list) {
// 先加左括号
if (left > 0) {
generate(left - 1, right, current + "(", list);
}
if (right > 0 && right > left) {
generate(left, right - 1, current + ")", list);
}
if (left == 0 && right == 0) {
list.add(current);
}
}

generateParenthesis

相关链接:

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

https://github.com/Gerrard-Feng/LeetCode/blob/master/LeetCode/src/com/gerrard/algorithm/medium/Q022.java

PS:如有不正确或提高效率的方法,欢迎留言,谢谢!

No.022:Generate Parentheses的更多相关文章

  1. LeetCode OJ:Generate Parentheses(括号生成)

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

  2. LeetCode第[22]题(Java):Generate Parentheses

    题目:制造括号序列 难度:Medium 题目内容: Given n pairs of parentheses, write a function to generate all combination ...

  3. LeetCode 022 Generate Parentheses

    题目描述:Generate Parentheses Given n pairs of parentheses, write a function to generate all combination ...

  4. 72. Generate Parentheses && Valid Parentheses

    Generate Parentheses Given a string containing just the characters '(', ')', '{', '}', '[' and ']', ...

  5. Generate Parentheses

    Generate Parentheses Given n pairs of parentheses, write a function to generate all combinations of ...

  6. [LintCode] Generate Parentheses 生成括号

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

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

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

  8. 【题解】【排列组合】【回溯】【Leetcode】Generate Parentheses

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

  9. leetcode022. Generate Parentheses

    leetcode 022. Generate Parentheses Concise recursive C++ solution class Solution { public: vector< ...

随机推荐

  1. IOS SWIFT 启动流程学习

    其实和我们java.c一样通过一个main函数作为入口. main封装在了UIApplicationMain里面.所以后者变成启动入口. 他会扫描Info.plist,找到需要加载的入口storybo ...

  2. 启动 Apache2.2 的问题

    启动 Apache2.2 的问题: windows不能在本地计算机启动 Apache2.2.有关更多信息,查阅系统事件日志.如果这是非Microsoft服务,请与服务厂商联系,并参考特定服务错误代码1 ...

  3. 机器学习理论知识部分--偏差方差平衡(bias-variance tradeoff)

    摘要: 1.常见问题 1.1 什么是偏差与方差? 1.2 为什么会产生过拟合,有哪些方法可以预防或克服过拟合? 2.模型选择例子 3.特征选择例子 4.特征工程与数据预处理例子 内容: 1.常见问题 ...

  4. Atitti  onvif 设备发现与原理

    Atitti  onvif 设备发现与原理 1.1. ,有以下几个步骤:1 1.2. 设备搜索原理及编程技巧:2 1.3. Ws disconvert 的组播地址和端口就是37022 1)发现ipca ...

  5. CSS3盒模型display:box;box-flex:3;

    <!DOCTYPE html> <html> <head> <meta charset="utf-8"> <meta name ...

  6. 《Qt Quick 4小时入门》学习笔记4

    http://edu.csdn.net/course/detail/1042/14806?auto_start=1 Qt Quick 4小时入门 第七章:处理鼠标与键盘事件 1.处理鼠标事件 鼠标信号 ...

  7. JS原生第五篇 (帅哥)

    1.1 节点 1. 节点        网页是有很多的节点组成的  . 元素节点   指的是 :  标签     li  span 文本节点      属性节点 父子兄弟    父    parent ...

  8. Sql Server系列:系统函数

    1. 返回表中指定字段的长度值COL_LENGTH 返回列的定义长度(以字节为单位). 语法: COL_LENGTH ( 'table' , 'column' ) 示例: SELECT COL_LEN ...

  9. Python标准模块--functools

    1 模块简介 functools,用于高阶函数:指那些作用于函数或者返回其它函数的函数,通常只要是可以被当做函数调用的对象就是这个模块的目标. 在Python 2.7 中具备如下方法, cmp_to_ ...

  10. C#单例模式详解

    C#要实现单例模式必须要有以下三点: 声明私有静态成员.私有化构造函数.静态函数返回实例. private static GameManager s_GameManager=null; private ...