leetcode第32題:最長有效括號(遇到一個奇葩的錯誤)
阿新 • • 發佈:2018-11-01
問題描述:
給一個只包含 '('
和 ')'
的字串,找出最長的有效(正確關閉)括號子串的長度。
對於 "(()"
,最長有效括號子串為 "()"
,它的長度是 2。
另一個例子 ")()())"
,最長有效括號子串為 "()()"
,它的長度是 4。
思路很簡單:棧回溯,分為情況討論
對於當前字元,如果是"(",直接壓入棧中。如果是")",要分以下幾種情況討論:
(1)如果當前棧為空,說明不存在與當前右括號配對的左括號,直接continue.
(2)如果當前棧大小為1:
a.如果棧頂元素是"(",則找到一個有效的括號序列,彈出棧頂元素,並壓入這個序列的長度2;
b.如果棧頂元素是數字,說明不存在與當前右括號配對的左括號,且由於插入了一個右括號,之前得到的括號序列無法更長,需要彈出棧頂元素。
(3)如果當前棧的大小大於等於2:
彈出棧頂元素
a.如果是"(",則找到一個為2的有效序列,再檢查棧頂元素,如果是數字,說明可以與前面找到的括號序列合併為一個更大的序列,與其相加後壓入棧,否則直接將2壓入棧;
b.如果是數字,由於當前的棧大小大於等於2,則下一個棧的元素一定是“(”,彈出後壓入合併後的序列長度,壓之前再檢查,如果棧頂元素還是為數字,則再合併,再壓入。
程式碼如下:
int longestValidParentheses(string s) { int max = 0,len = s.size(); stack<int> st_aux; for(int i = 0; i < len; i++){ if(s[i] == '(')st_aux.push(0);//注意這裡不能直接push('(');因為‘('ascii碼為40,如果剛好累計長度到40,則使判據混亂,這裡卡了好久啊 if(s[i] == ')'){ if(st_aux.empty())continue; else if(st_aux.size() == 1){ if(st_aux.top() == 0){ st_aux.pop(); st_aux.push(2); max = 2 < max?2:max; } else st_aux.pop(); } else { int temp = 0; if(st_aux.top() == 0){ st_aux.pop(); temp = 2; st_aux.push(temp); } else{ temp = st_aux.top(); st_aux.pop(); st_aux.pop(); temp += 2; st_aux.push(temp); } temp = 0; while(!st_aux.empty()&&st_aux.top() != 0){ temp += st_aux.top(); st_aux.pop(); } st_aux.push(temp); if(temp > max)max = temp; } } } return max; }
注意這裡不能直接push('(');因為‘('ascii碼為40,如果剛好累計長度到40,則使判據混亂,這裡卡了好久啊。
方法二:動態規劃,請看連結
https://blog.csdn.net/u010232171/article/details/44728535