標籤:
這個題目leetcode上提示用動態規劃,但是那樣要O(n^2)。我自己想出了一個O(n)的演算法,並提交通過。
【題目】
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.Tags: Dynamic Programming ,String
【思路】
注意到一個規律:只要從開頭當前位置的子串中左括弧的個數小於右括弧的個數,那麼該子串便不能夠再同右邊任何子串構成合法子串。
這時,只要記錄當前子串的最長合法子串,然後從下一個位置開始尋找最長子串。
局部最長合法子串長度的記錄:這裡用到了一個Hashtable<Integer,Integer>,key為記錄該長度時棧中左括弧的個數,value為每次遇
到右括弧時該右括弧所在合法子串的長度。
【上碼】
import java.util.Hashtable;import java.util.Stack;/* * 參考:為參考他人演算法 * T = O(n) * leetcode上提示用動態規劃,但是那樣要O(n^2) */public class Solution {public int longestValidParentheses(String s) {int maxLen = 0;if(s==null||s.length()==0)return maxLen;Stack<Character> stack = new Stack<Character>();Hashtable<Integer, Integer> hashtable = new Hashtable<Integer, Integer>();int len = s.length();int left=0,right=0,L=0;for(int p=0;p<len;p++){if(s.charAt(p) == ')')if(stack.isEmpty()){//maxLen = maxLen>L?maxLen:L;right++;}else if(stack.peek()=='('){stack.pop();Integer v1 = hashtable.get(left);if(v1 != null){L += v1;hashtable.remove(left);}left--;L+=2;Integer v2 = hashtable.get(left);if(v2 != null){L += v2;}hashtable.put(left, L);}else {stack.push(')');right++;}else {stack.push('(');left++;}maxLen = maxLen>L?maxLen:L;L = 0;if(left<right){stack.clear();hashtable.clear();left = 0;right = 0;//L = 0;}}return maxLen;}}
【leetcode with java】32 Longest Valid Parentheses O(n)