leetcode困难32最长有效括号

Posted qq_40707462

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了leetcode困难32最长有效括号相关的知识,希望对你有一定的参考价值。


思路:栈

  • 用栈模拟一遍,将所有无法匹配的括号的位置全部置1
  • 例如: "()(()"的 mark 为[0, 0, 1, 0, 0]
    再例如: ")()((())"的 mark 为[1, 0, 0, 1, 0, 0, 0, 0]
  • 经过这样的处理后, 此题就变成了寻找最长的连续的0的长度

匹配过程:

  • 遇到左括号,(下标)入栈
  • 遇到右括号,栈为空则mark该下标,不为空则从栈里删除一个左括号
  • 最后栈里未匹配完的左括号,下标处都mark
class Solution 
    public int longestValidParentheses(String s) 
        int[]mark=new int[s.length()];
        List<Integer>stack=new ArrayList<>();
        for(int i=0;i<s.length();i++)
            if(s.charAt(i)=='(') stack.add(i);
            else
                if(stack.isEmpty()) mark[i]=1;//不能配对,标记
                else stack.remove(stack.size()-1);
            
        
        //未匹配完的括号,标记
        while(!stack.isEmpty())
            mark[stack.remove(stack.size()-1)]=1;
        
        //寻找最长的0
        int len=0,res=0;
        for(int i=0;i<s.length();i++)
            if(mark[i]==1)
                len=0;
                continue;
            
            len++;
            res=Math.max(res,len);
        
        return res;
    

优化:不用mark数组,边遍历,边计算当前最大
始终保持栈底元素为当前已经遍历过的元素中「最后一个没有被匹配的左括号的下标」
需要注意的是,如果一开始栈为空,第一个字符为右括号的时候我们会将其放入栈中,这样就不满足提及的「最后一个没有被匹配的左括号的下标」,为了保持统一,我们在一开始的时候往栈中放入一个值为 -1 的元素。

class Solution 
    public int longestValidParentheses(String s) 
        int res = 0;
        List<Integer> stack = new ArrayList<>();
        stack.add(-1);
        for (int i = 0; i < s.length(); i++) 
            if (s.charAt(i) == '(') 
                stack.add(i);
             else 
                stack.remove(stack.size()-1);
                if (stack.isEmpty()) 
                    stack.add(i);
                 else 
                    res = Math.max(res, i - stack.get(stack.size()-1));
                
            
        
        return res;
    

以上是关于leetcode困难32最长有效括号的主要内容,如果未能解决你的问题,请参考以下文章

32. 最长有效括号(困难)-字节跳动高频题

[Leetcode] 32.最长有效括号

leetcode 32: 最长有效括号

leetcode32 最长有效括号(Hard)

Leetcode(32)-最长有效括号

Leetcode_32最长有效括号