一. 括號問題一般可以藉助棧這種數據結構解決, 先進後出保證這一性質.
二. 因爲求子串的長度, 因此我們可以在棧中保存index(序號)來方便求長度.
三, 看棧的出棧和入棧, 時間複雜度爲O(n).
class Solution {
public:
int longestValidParentheses(string s) {
int len = s.length();
stack<int> st;
//適用於當棧沒有元素的時候,減少判斷,因爲我們算長度
//是根據匹配的括號的前一個來進行計算的.
st.push(-1);
int result = 0;
for (int i=0;i<len;i++) {
//當有可匹配的括號時,
//記錄答案爲當前位置和匹配的
//元素的前一個位置計算長度.
//這裏算的是距離.
if (s[i]==')' && st.size()>1 && s[st.top()]=='('){
st.pop();
result = max(result, i-st.top());
}
//其他情況直接入棧.
else st.push(i);
}
return result;
}
};
四. 字符串的問題通常還可以借用動態規劃的思路.
五. 定義dp[i] 爲 str[0...i]的以 i 結尾的字符串的最長有效括號.
class Solution {
public:
int longestValidParentheses(string s) {
int len = s.length();
//邊界條件
if(len<=1) return 0;
//定義dp[len+1], 其中dp[0]是0,防止出界.
vector<int> dp(len+1,0);
int maxV = 0;
//從2開始,因爲dp[1]=0,一個括號結果肯定是0.
for(int i=2;i<=len;i++) {
//注意用在字符串的位置上時,i應該減1,因爲字符串從0開始.
//以'('結尾的字符串爲0.
if(s[i-1]=='(') dp[i] = 0;
else {
//以')'結尾字符串,如果前一個是'(',說明配對.
//哪怕形如"()",因爲我們dp[0]爲0,所以不用
//再次判斷了.
if(s[i-2]=='(') dp[i] = dp[i-2]+2;
else{
//如果形如"))",dp[i-1]是以i-1結尾的有效個數,
//因此i-dp[i-1]-1, 代表不能配對的那一個.如果
//沒有越界並且它是'(', 則如公式所示.
//別忘記加上前面匹配的括號數目,dp[i-dp[i-1]-2].
//否則是0.
if(i-dp[i-1]-2>=0 && s[i-dp[i-1]-2]=='(')
dp[i] = dp[i-1]+2+dp[i-dp[i-1]-2];
else dp[i] = 0;
}
//找到最大的dp[i].
maxV = max(maxV, dp[i]);
}
}
return maxV;
}
};
六. 時間複雜度清晰看出爲O(n).