最长有效括号

问题描述:

给定一个只包含 ‘(’ 和 ‘)’ 的字符串,找出最长的包含有效括号的子串的长度。

示例1:

输入: “(()”
输出: 2
解释: 最长有效括号子串为 “()”

示例2:

输入: “)()())”
输出: 4
解释: 最长有效括号子串为 “()()”

问题分析:

用数组dp[i]表示括号串s[i]结尾的最大括号字串长度。
当 s[ i ] 是’ ( '时, dp[i]一定为0。

当s[ i ]为‘ ) ‘时,判断s[i-1]是否为‘( ’
s[i-1]==’(’ :
则dp[i] = dp[i-2]+2 (i-2)>=0。dp[i]=2, (i-2)<0。
s[i-1]!=’('
此时判断s[i-1-dp[i-1]] 是否为’(’
类似于 (()()), s[i-1-dp[i-1]]其实就是s[i]前面第一个不在有效子串中的括号
应注意需要[i-1-dp[i-1]>=0

如果s[i-1-dp[i-1]]==’ ( ’
dp[i] = dp[i-1]+2 +dp[i-1-dp[i-1]-1] ; (i-1-dp[i-1]-1)>0
dp[i] = dp[i-1]+2 ; (i-1-dp[i-1]-1)<=0

类似于 ()(()()) 最后一个在4的基础上+2后应该加上最前面的两个, 所以 在s[i-1]的基础上加2后 应该加上dp[i-1dp[i-1]-1] 。

其它情况下dp[i]=0;

过程:

      if(s[i]='(')
             dp[i] = 0;
        else {
            if(s[i-1]=='('){
                if((i-2)>0)
                  		dp[i]= dp[i-2]+2;
                  else
                  		dp[i] = 2;
            }
            else{
            			if((i-1-dp[i-1])>=0&&s[i-1-dp[i-1]]=='(') {
            				  if(i-1-dp[i-1]-1>0)
              					dp[i] = dp[i-1]+2+ dp[i-1-dp[i-1]-1];
              			else
              					dp[i]  = dp[i-1]+2;
            				}            
            			else
            				dp [i]=0;				
            }
         }

代码:

package DP;
/*
最长有效括号
 */
public class L32 {

    public static int   longestValidParentheses(String s){
           int dp[] = new int [s.length()];
           if(s==null||s.equals(""))
               return 0;
           int max= 0 ;
           dp[0]=0;
           for(int i=1;i<s.length();i++){
               if(s.charAt(i)=='(')    //最后一个字符是“(”
                   dp[i]=0;
               else{          // 最后一个字符是") "
                   if(s.charAt(i-1)=='(') {
                       if (i - 2 > 0)
                           dp[i] = dp[i - 2] + 2;
                       else
                           dp[i] = 2;
                   }
                   else{
                       if((i-1-dp[i-1]>=0)&&s.charAt(i-1-dp[i-1])=='('){
                           if(i-1-dp[i-1]-1>0){
                               dp[i] = dp[i-1]+2+dp[i-1-dp[i-1]-1];
                           }
                           else{
                               dp[i]=  dp[i-1]+2;
                           }

                       }
                       else{
                           dp[i]=0;
                       }
                   }

               }
            max = max>dp[i]?max:dp[i];

           }

        return max;
    }

    public static void main(String[] args) {
        String s  = "((()))";
        System.out.print(longestValidParentheses(s));
    }
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值