zoukankan      html  css  js  c++  java
  • 最长双回文串

     最长双回文串

    题目描述

    顺序和逆序读起来完全一样的串叫做回文串。比如acbca是回文串,而abc不是(abc的顺序为“abc”,逆序为“cba”,不相同)。
    输入长度为n的串S,求S的最长双回文子串T,即可将T分为两部分X,Y,(|X|,|Y|≥1)且X和Y都是回文串。

    对于$10%$的数据, $ 2≤|S|≤10^3 $。
    对于$30%$的数据,$ 2≤|S|≤10^4 $。
    对于$100%$的数据,$ 2≤|S|≤10^5 $。

    Solution
    先manache求出每个位置为中心的最长回文串,把中心的位置打在左端点上。
    从左到右取一边Max,求出每一个位置x覆盖它的最右位置p[x]。
    接着访问每一个中心x,取他的右端点xr,则ans= max(ans,p[xr]-x);相当于拼起来
     
    我的做法是非正解。。没过的同学可以看看别人的。
    我们oj数据弱可以过,洛谷过不了。
    有没有神犇看看为啥错?或者出数据卡卡。
    博主不胜感激。
     1 #include<cstdio>
     2 #include<iostream>
     3 #include<cstdlib>
     4 #include<cstring>
     5 #include<algorithm>
     6 #include<cmath>
     7 #define maxn 1000000
     8 using namespace std;
     9 int n,p[maxn],Max[maxn];
    10 char ch[maxn],s[maxn]; 
    11 int main()
    12 {
    13     scanf(" %s",ch+1);n=strlen(ch+1);
    14     for(int i=1;i<=n;i++){
    15         s[i+i]=ch[i];s[i+i+1]='%';
    16     }
    17     int mr=0,id=0;s[0]='%';s[1]='%';s[n+n+2]='
    ';n=n+n+1;
    18     for(int i=1;i<=n;i++){
    19         p[i]=mr>i?min(p[2*id-i],mr-i):1;
    20         while(s[i+p[i]]==s[i-p[i]])p[i]++;
    21         if(i+p[i]>mr){
    22             mr=i+p[i];
    23             id=i;
    24             
    25         }
    26         Max[i-p[i]]=max(Max[i-p[i]],id);
    27         //cout<<i<<' '<<p[i]<<endl;
    28     }
    29     for(int i=1;i<=n;i++)Max[i]=max(Max[i],Max[i-1]);
    30     int ans=0;
    31     for(int i=1;i<=n;i++){
    32         ans=max(ans,Max[i+p[i]-1]-i);
    33     }
    34     cout<<ans<<endl;
    35     return 0;
    36 }
    View Code
     
  • 相关阅读:
    Hive join操作优化
    php中 date 函数中的格式参数
    Mysql分表之后的聚合统计
    使用Elasticsearch-Dump工具复制ES库
    Json Path 语法详解(Java)
    Json Path 语法
    关于qt5.2~qt5.8的下载地址
    RTL8812AU双频无线网卡在ubuntu19和20上的驱动安装
    使用vscode对threejs的本地调试
    ThreeJS中创建文字的几种方法
  • 原文地址:https://www.cnblogs.com/liankewei/p/10662946.html
Copyright © 2011-2022 走看看