最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

C++實(shí)現(xiàn)LeetCode(32.最長(zhǎng)有效括號(hào))

 更新時(shí)間:2021年07月14日 11:21:50   作者:Grandyang  
這篇文章主要介紹了C++實(shí)現(xiàn)LeetCode(32.最長(zhǎng)有效括號(hào)),本篇文章通過(guò)簡(jiǎn)要的案例,講解了該項(xiàng)技術(shù)的了解與使用,以下就是詳細(xì)內(nèi)容,需要的朋友可以參考下

[LeetCode] 32. Longest Valid Parentheses 最長(zhǎng)有效括號(hào)

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

Example 1:

Input: "(()"
Output: 2
Explanation: The longest valid parentheses substring is "()"

Example 2:

Input: ")()())"
Output: 4
Explanation: The longest valid parentheses substring is "()()"

這道求最長(zhǎng)有效括號(hào)比之前那道 Valid Parentheses 難度要大一些,這里還是借助棧來(lái)求解,需要定義個(gè) start 變量來(lái)記錄合法括號(hào)串的起始位置,遍歷字符串,如果遇到左括號(hào),則將當(dāng)前下標(biāo)壓入棧,如果遇到右括號(hào),如果當(dāng)前棧為空,則將下一個(gè)坐標(biāo)位置記錄到 start,如果棧不為空,則將棧頂元素取出,此時(shí)若棧為空,則更新結(jié)果和 i - start + 1 中的較大值,否則更新結(jié)果和 i - st.top() 中的較大值,參見(jiàn)代碼如下:

解法一:

class Solution {
public:
    int longestValidParentheses(string s) {
        int res = 0, start = 0, n = s.size();
        stack<int> st;
        for (int i = 0; i < n; ++i) {
            if (s[i] == '(') st.push(i);
            else if (s[i] == ')') {
                if (st.empty()) start = i + 1;
                else {
                    st.pop();
                    res = st.empty() ? max(res, i - start + 1) : max(res, i - st.top());
                }
            }
        }
        return res;
    }
};

還有一種利用動(dòng)態(tài)規(guī)劃 Dynamic Programming 的解法。這里使用一個(gè)一維 dp 數(shù)組,其中 dp[i] 表示以 s[i-1] 結(jié)尾的最長(zhǎng)有效括號(hào)長(zhǎng)度(注意這里沒(méi)有對(duì)應(yīng) s[i],是為了避免取 dp[i-1] 時(shí)越界從而讓 dp 數(shù)組的長(zhǎng)度加了1),s[i-1] 此時(shí)必須是有效括號(hào)的一部分,那么只要 dp[i] 為正數(shù)的話,說(shuō)明 s[i-1] 一定是右括號(hào),因?yàn)橛行Юㄌ?hào)必須是閉合的。當(dāng)括號(hào)有重合時(shí),比如 "(())",會(huì)出現(xiàn)多個(gè)右括號(hào)相連,此時(shí)更新最外邊的右括號(hào)的 dp[i] 時(shí)是需要前一個(gè)右括號(hào)的值 dp[i-1],因?yàn)榧偃?dp[i-1] 為正數(shù),說(shuō)明此位置往前 dp[i-1] 個(gè)字符組成的子串都是合法的子串,需要再看前面一個(gè)位置,假如是左括號(hào),說(shuō)明在 dp[i-1] 的基礎(chǔ)上又增加了一個(gè)合法的括號(hào),所以長(zhǎng)度加上2。但此時(shí)還可能出現(xiàn)的情況是,前面的左括號(hào)前面還有合法括號(hào),比如 "()(())",此時(shí)更新最后面的右括號(hào)的時(shí)候,知道第二個(gè)右括號(hào)的 dp 值是2,那么最后一個(gè)右括號(hào)的 dp 值不僅是第二個(gè)括號(hào)的 dp 值再加2,還可以連到第一個(gè)右括號(hào)的 dp 值,整個(gè)最長(zhǎng)的有效括號(hào)長(zhǎng)度是6。所以在更新當(dāng)前右括號(hào)的 dp 值時(shí),首先要計(jì)算出第一個(gè)右括號(hào)的位置,通過(guò) i-3-dp[i-1] 來(lái)獲得,由于這里定義的 dp[i] 對(duì)應(yīng)的是字符 s[i-1],所以需要再加1,變成 j = i-2-dp[i-1],這樣若當(dāng)前字符 s[i-1] 是左括號(hào),或者j小于0(說(shuō)明沒(méi)有對(duì)應(yīng)的左括號(hào)),或者 s[j] 是右括號(hào),此時(shí)將 dp[i] 重置為0,否則就用 dp[i-1] + 2 + dp[j] 來(lái)更新 dp[i]。這里由于進(jìn)行了 padding,可能對(duì)應(yīng)關(guān)系會(huì)比較暈,大家可以自行帶個(gè)例子一步一步執(zhí)行,應(yīng)該是不難理解的,參見(jiàn)代碼如下:

解法二:

class Solution {
public:
    int longestValidParentheses(string s) {
        int res = 0, n = s.size();
        vector<int> dp(n + 1);
        for (int i = 1; i <= n; ++i) {
            int j = i - 2 - dp[i - 1];
            if (s[i - 1] == '(' || j < 0 || s[j] == ')') {
                dp[i] = 0;
            } else {
                dp[i] = dp[i - 1] + 2 + dp[j];
                res = max(res, dp[i]);
            }
        }
        return res;
    }
};

此題還有一種不用額外空間的解法,使用了兩個(gè)變量 left 和 right,分別用來(lái)記錄到當(dāng)前位置時(shí)左括號(hào)和右括號(hào)的出現(xiàn)次數(shù),當(dāng)遇到左括號(hào)時(shí),left 自增1,右括號(hào)時(shí) right 自增1。對(duì)于最長(zhǎng)有效的括號(hào)的子串,一定是左括號(hào)等于右括號(hào)的情況,此時(shí)就可以更新結(jié)果 res 了,一旦右括號(hào)數(shù)量超過(guò)左括號(hào)數(shù)量了,說(shuō)明當(dāng)前位置不能組成合法括號(hào)子串,left 和 right 重置為0。但是對(duì)于這種情況 "(()" 時(shí),在遍歷結(jié)束時(shí)左右子括號(hào)數(shù)都不相等,此時(shí)沒(méi)法更新結(jié)果 res,但其實(shí)正確答案是2,怎么處理這種情況呢?答案是再反向遍歷一遍,采取類似的機(jī)制,稍有不同的是此時(shí)若 left 大于 right 了,則重置0,這樣就可以 cover 所有的情況了,參見(jiàn)代碼如下:

解法三:

class Solution {
public:
    int longestValidParentheses(string s) {
        int res = 0, left = 0, right = 0, n = s.size();
        for (int i = 0; i < n; ++i) {
            (s[i] == '(') ? ++left : ++right;
            if (left == right) res = max(res, 2 * right);
            else if (right > left) left = right = 0;
        }
        left = right = 0;
        for (int i = n - 1; i >= 0; --i) {
            (s[i] == '(') ? ++left : ++right;
            if (left == right) res = max(res, 2 * left);
            else if (left > right) left = right = 0;
        }
        return res;
    }
};

到此這篇關(guān)于C++實(shí)現(xiàn)LeetCode(32.最長(zhǎng)有效括號(hào))的文章就介紹到這了,更多相關(guān)C++實(shí)現(xiàn)最長(zhǎng)有效括號(hào)內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • 關(guān)于移位操作的一點(diǎn)重要說(shuō)明

    關(guān)于移位操作的一點(diǎn)重要說(shuō)明

    下面小編就為大家?guī)?lái)一篇關(guān)于移位操作的一點(diǎn)重要說(shuō)明。小編覺(jué)得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧
    2016-12-12
  • C++實(shí)現(xiàn)將一個(gè)字符串中的字符替換成另一個(gè)字符串的方法

    C++實(shí)現(xiàn)將一個(gè)字符串中的字符替換成另一個(gè)字符串的方法

    這篇文章主要介紹了C++實(shí)現(xiàn)將一個(gè)字符串中的字符替換成另一個(gè)字符串的方法,需要考慮的情況比較全面,有不錯(cuò)的借鑒價(jià)值,需要的朋友可以參考下
    2014-09-09
  • C語(yǔ)言函數(shù)超詳細(xì)講解上篇

    C語(yǔ)言函數(shù)超詳細(xì)講解上篇

    函數(shù)是一組一起執(zhí)行一個(gè)任務(wù)的語(yǔ)句。每個(gè)?C?程序都至少有一個(gè)函數(shù),即主函數(shù)?main()?,所有簡(jiǎn)單的程序都可以定義其他額外的函數(shù),函數(shù)我們分兩篇來(lái)講解,接下來(lái)開(kāi)始第一篇
    2022-04-04
  • C++實(shí)現(xiàn)順序排序算法簡(jiǎn)單示例代碼

    C++實(shí)現(xiàn)順序排序算法簡(jiǎn)單示例代碼

    這篇文章主要介紹了C++實(shí)現(xiàn)順序排序算法簡(jiǎn)單示例代碼,對(duì)于學(xué)過(guò)C++的朋友一定不會(huì)陌生,現(xiàn)在重溫一下這個(gè)算法,需要的朋友可以參考下
    2014-08-08
  • OpenCV實(shí)現(xiàn)拼圖算法

    OpenCV實(shí)現(xiàn)拼圖算法

    這篇文章主要為大家詳細(xì)介紹了OpenCV實(shí)現(xiàn)拼圖算法,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2021-07-07
  • VS2010+Opencv+MFC讀取圖像和視頻顯示在Picture控件

    VS2010+Opencv+MFC讀取圖像和視頻顯示在Picture控件

    這篇文章主要為大家詳細(xì)介紹了VS2010+Opencv+MFC讀取圖像和視頻顯示在Picture控件,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2019-08-08
  • 深入解析C語(yǔ)言中的內(nèi)存分配相關(guān)問(wèn)題

    深入解析C語(yǔ)言中的內(nèi)存分配相關(guān)問(wèn)題

    這篇文章主要深入地介紹了C語(yǔ)言中的內(nèi)存分配,C語(yǔ)言編程中的內(nèi)存泄漏問(wèn)題一直以來(lái)都是C編程中的一大棘手問(wèn)題,本文從malloc和指針等方面對(duì)C內(nèi)存進(jìn)行了深層次講解,強(qiáng)烈推薦!需要的朋友可以參考下
    2015-08-08
  • 詳解在VScode中添加代碼塊(含C++指令生成代碼)

    詳解在VScode中添加代碼塊(含C++指令生成代碼)

    這篇文章主要介紹了詳解在VScode中添加代碼塊(含C++指令生成代碼),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2021-04-04
  • C++實(shí)現(xiàn)Dijkstra(迪杰斯特拉)算法

    C++實(shí)現(xiàn)Dijkstra(迪杰斯特拉)算法

    這篇文章主要為大家詳細(xì)介紹了C++實(shí)現(xiàn)Dijkstra(迪杰斯特拉)算法,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2020-05-05
  • C語(yǔ)言實(shí)現(xiàn)騎士飛行棋小游戲

    C語(yǔ)言實(shí)現(xiàn)騎士飛行棋小游戲

    這篇文章主要為大家詳細(xì)介紹了C語(yǔ)言實(shí)現(xiàn)騎士飛行棋小游戲,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2020-02-02

最新評(píng)論

沅陵县| 伊宁县| 岳西县| 武山县| 松江区| 昌都县| 台中县| 富顺县| 嘉荫县| 乐昌市| 韩城市| 汕头市| 梁平县| 永仁县| 三明市| 福建省| 原阳县| 普安县| 惠东县| 海兴县| 朝阳市| 吴忠市| 大姚县| 湛江市| 夏津县| 锡林郭勒盟| 灯塔市| 疏勒县| 自治县| 章丘市| 琼中| 渝北区| 扎赉特旗| 焉耆| 成都市| 吴川市| 赞皇县| 冷水江市| 万荣县| 汕头市| 屯昌县|