zoukankan      html  css  js  c++  java
  • Leetcode | Parentheses 相关

    Generate Parentheses

    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就可以添加左括号。只要右括号数大于左括号数就可以添加右括号。

     1 class Solution {
     2 public:
     3     vector<string> generateParenthesis(int n) {
     4         vector<string> res;
     5         
     6         recursive(n, n, "", res);
     7         
     8         return res;
     9     }
    10     
    11     void recursive(int n1, int n2, string str, vector<string> &res) {
    12         if (n1 == 0 && n2 == 0) {
    13             res.push_back(str);
    14             return;
    15         }
    16         
    17         if (n1 >= 1) {
    18             recursive(n1 - 1, n2, str + "(", res);
    19         }
    20         
    21         if (n2 > n1) {
    22             recursive(n1, n2 - 1, str + ")", res);
    23         }
    24     }
    25 };

     网上查了一下,竟然还和Catalan数有关。

    通项公式是: (frac{(2n)!}{(n+1)!n!}) 

    递推公式是 (C_0=1 and C_{n+1}=sumlimits^n_{i=0}{C_{i}C_{n-i}})

    n个+1和n个-1构成2n项(a_1,a_2,ldots,a_n),其部分和满足(a_1+a_2+ldots+a_kge{}0,0le{}kle{}2n)的序列个数等于第n个Catalan数(C_n)

    Valid Parentheses

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

    The brackets must close in the correct order, "()" and "()[]{}" are all valid but "(]" and "([)]" are not.

    用了一个栈去实现。当前哪果是右括号,那么栈顶必须是对应的左括号才行。栈为空的话,也只能push左括号。

     1 class Solution {
     2 public:
     3     bool isValid(string s) {
     4         if (s.empty()) return true;
     5         
     6         stack<char> st;
     7         
     8         for (int i = 0; i < s.length(); ++i) {
     9             if (st.empty()) {
    10                 if (s[i] == '(' || s[i] == '[' || s[i] == '{')  st.push(s[i]);
    11                 else return false;
    12             } else if (s[i] == '(' || s[i] == '[' || s[i] == '{') {
    13                 st.push(s[i]);
    14             } else if (s[i] == ')') {
    15                 if (st.top() == '(') st.pop();
    16                 else return false;
    17             } else if (s[i] == ']') {
    18                 if (st.top() == '[') st.pop();
    19                 else return false;
    20             } else if (s[i] == '}') {
    21                 if (st.top() == '{') st.pop();
    22                 else return false;
    23             } else {
    24                 return false;
    25             }
    26         }
    27         return st.empty();
    28     }
    29 };

    重构一下:

     1 class Solution {
     2 public:
     3     bool isValid(string s) {
     4         if (s.empty()) return true;
     5         
     6         stack<char> st;
     7         
     8         for (int i = 0; i < s.length(); ++i) {
     9             if (s[i] == '(' || s[i] == '[' || s[i] == '{') {
    10                 st.push(s[i]);
    11                 continue;
    12             } else if (st.empty()) {
    13                 return false;
    14             } 
    15             
    16             if (s[i] == ')' && st.top() != '(') return false;
    17             if (s[i] == ']' && st.top() != '[') return false;
    18             if (s[i] == '}' && st.top() != '{') return false;
    19             st.pop();
    20         }
    21         return st.empty();
    22     }
    23 };

     用map再重构,可以再简洁一些。

     1 class Solution {
     2 public:
     3     bool isValid(string s) {
     4         if (s.empty()) return true;
     5         
     6         map<char, char> pars;
     7         pars[')'] = '(';
     8         pars[']'] = '[';
     9         pars['}'] = '{';
    10         
    11         stack<char> st;
    12         
    13         for (int i = 0; i < s.length(); ++i) {
    14             if (pars.find(s[i]) == pars.end()) {
    15                 st.push(s[i]);
    16                 continue;
    17             } if (st.empty()) {
    18                 return false;
    19             } 
    20             
    21             if (st.top() != pars[s[i]]) return false;
    22             st.pop();
    23         }
    24         return st.empty();
    25     }
    26 };

     Longest Valid Parentheses

    Given a string containing just the characters '(' and ')', find the length of the longest valid (well-formed) parentheses substring.

    For "(()", the longest valid parentheses substring is "()", which has length = 2.

    Another example is ")()())", where the longest valid parentheses substring is "()()", which has length = 4.

    一开始就把思路定在,当碰到一个“(”右括号时,判断当前已经能够消掉的位置。后面也想过把值和位置作一个新的struct push到stack中,但是怎么就是想不到直接在stack中存位置呢。。。。

    应该多思考一下和前面Valid Parentheses的关系。

    总结思路就在于:

    1. 栈顶为"(",当前字符为")",这时就可出栈,同时记录当前消掉的长度;栈如果为空的话表明前面的符号全部被消掉了,所以长度就为i+1. 否则就是pop之后的新栈顶到当前位置的距离。也就是st.pop(); i - st.top(); 

    2. 要检查栈顶,那么st不能为空。

     1 class Solution {
     2 public:
     3     int longestValidParentheses(string s) {
     4         if (s.empty()) return 0;
     5         
     6         int max = 0;
     7         stack<int> st;
     8         
     9         for (int i = 0; i < s.length(); ++i) {
    10             if (st.empty()) {
    11                 st.push(i);
    12             } else {
    13                 if (s[st.top()] == '(' && s[i] == ')') {
    14                     st.pop();
    15                     if (st.empty()) {
    16                         if (i + 1 > max) max = i + 1;
    17                     } else if (i - st.top() > max) {
    18                         max = i - st.top();
    19                     }
    20                 } else {
    21                     st.push(i);
    22                 }
    23             }
    24         }
    25         
    26         return max;       
    27     }
    28 };

    第三次写,用栈。

     1 class Solution {
     2 public:
     3     int longestValidParentheses(string s) {
     4         if (s.empty()) return 0;
     5         stack<int> st;
     6         
     7         int max = 0;
     8         for (int i = 0; i < s.length(); i++) {
     9             if (st.empty() || s[i] == '(') {
    10                 st.push(i);
    11             } else if (s[st.top()] == '(') {
    12                 st.pop();
    13                 int len = st.empty() ? i + 1 : i - st.top();
    14                 if (len > max) max = len;
    15             } else {
    16                 st.push(i);
    17             } 
    18         }
    19         
    20         return max;
    21     }
    22 };

    这种求longest、maximum之类的题大多数也是可以用dp来做。

     dp[i]表示到第i个位置的最长合法串。

    1. 初始值都为0. 第一个符号无影响,所以可以从第二个位置开始。

    2. 举例说一下dp[i]的更新,假设s="()(()())"。

    i=7时,"()(()())";

    dp[i-1]=4就是到i-1=6为止的合法串长度,也就是"()(()())";

    此时需要检查j=i-dp[i-1]-1= 7-dp[6]-1=2的位置是否为"(","()(()())";

    如果是,那么dp[i]=dp[i-1]+2,dp[7]=dp[6]+2=6;

    此时还要把j之前的合法串合并起来。dp[i]+=dp[j-1], "()(()())",dp[7]+=dp[1]; dp[7]=8;

    所以答案就是8.

     1 class Solution {
     2 public:
     3     int longestValidParentheses(string s) {
     4         if (s.empty()) return 0;
     5         
     6         vector<int> dp(s.length(), 0);
     7         
     8         int max = 0;
     9         for (int i = 1; i < s.length(); ++i) {
    10             int j = i - dp[i - 1] - 1;
    11             if (s[i] == ')' && s[j] == '(') {
    12                 dp[i] = dp[i - 1] + 2;
    13                 if (j > 0) {
    14                     dp[i] += dp[j - 1];
    15                 }
    16                 if (dp[i] > max) max = dp[i];
    17             }
    18         }
    19         return max;
    20     }
    21 };
  • 相关阅读:
    sp2010 升级sp2013 用户无法打开网站
    powerviot install in sharepoint 2013
    can not connect cube in performancce dashboard
    westrac server security configure user info
    添加报表服务在多服务器场
    sharepoint 2013 office web app 2013 文档在线浏览 IE11 浏览器不兼容解决方法
    delete job definition
    目前付款申请单内网打开慢的问题
    item style edit in sharepoint 2013
    Could not load file or assembly '$SharePoint.Project.AssemblyFullName$'
  • 原文地址:https://www.cnblogs.com/linyx/p/3718955.html
Copyright © 2011-2022 走看看