LeetCode问题5

Longest Palindromic Substring

Given a string s, find the longest palindromic substring in s. You may assume that the maximum length of s is 1000.

最开始的采用了很暴力的方法如下:

class Solution {
    public String longestPalindrome(String s) {
        int i=0,j=0,length=s.length(),maxlength=0;
        int rei=0,rej=0;
        for (i=0;i<length;i++)
        {
            for (j=i;j<length;j++)
            {
                if(s.charAt(i)==s.charAt(j))
                {
                    if(isPalin(s.substring(i,j+1)))
                    {
                        if(j+1-i>maxlength)
                        {
                            maxlength=j+1-i;
                            rei=i;
                            rej=j+1;
                        }     
                    }
                }
            }
        }
        return s.substring(rei,rej);
    }
    boolean isPalin(String s)
    {
        int length=s.length();
        for(int i=0;i<length/2;i++)
        {
            if(s.charAt(i)==s.charAt(length-1-i));
            else
                return false;
        }
        return true;
    }
}

method isPalin()判断一个子字符串是否为回文的。

一个回文的字符串必定首尾相同,通过这个规律先减小部分计算量,只对首尾相同的子字符串判断是否回文。

简单的字符串可以应对,无规律的字符串也可以大程序减小计算量,但是对于bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb这种没有任何作用,运行结果:Time limitted exceeded。

LeetCode可以接受的时间复杂度为O(n^2),必须要采用一些策略:

1、对于一个从i到j的回文序列,它从i+1到j-1也必定是回文序列,可以利用这个方案提升效率。

2、从回文序列的中心下手。

提升效率后的代码:

 

//答案的算法
class Solution {
    public String longestPalindrome(String s) 
    {
        int i=0,length=s.length();
        int maxlength=0,templength=0,center=0;
        //中心在左边的情况
        for (i=0;i<length;i++)
        {
            templength=Palin(s.substring(0,i+1));
            if(maxlength<templength)
            {
                maxlength=templength;
                center=i;
            }
        }
        //中心在右边的情况
        for (i=length;i<2*length-1;i++)
        {
            templength=Palin(s.substring(i-length+1,length));
            if(maxlength<templength)
            {
                maxlength=templength;
                center=i;
            }
        }
        System.out.println(center);
        System.out.println(maxlength);
        if(center%2==0)
        {
            return s.substring(center/2-maxlength/2,center/2-maxlength/2+maxlength);//注意这里center/2-maxlength/2+maxlength不能简化成center/2+maxlength/2,考虑数据类型当center=0,maxlength=1,前式为1,后式为0;
        }
        else
        {
            return s.substring(center/2+1-maxlength/2,center/2+1-maxlength/2+maxlength);
        }
    }
    //s以中点为中心的回文最大长度
    //如abbab,返回1而非真正的4
    static int Palin(String s)
    {
        int length=s.length();
        int half=(length-1)/2;
        int i=half;
        //为利用中心的性质,必须从中间向两边计算,同时计数
        while(i>=0)
        {
            if(s.charAt(i)==s.charAt(length-i-1))
                i--;
            else
                break;                
        }
        if(length%2==0)
            return 2*(half-i);
        else 
            return 2*(half-i)-1;
    }
}
Palin(s.substring(i-length+1,length));
return s.substring(center/2-maxlength/2,center/2-maxlength/2+maxlength);

mad,水平好低,思路很简单,但是边界值处理要头脑清晰才行,上面两句调试了一段时间。

 

转载于:https://www.cnblogs.com/Einsler/p/7588607.html

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值