• Manachar's Algorithm


    1、模板

     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 const int MAX=21000020;
     4 char s[MAX],t[MAX<<1];
     5 int p[MAX<<1],cnt=0,mid,mr;
     6 void manachar()
     7 {
     8     t[cnt++]='$';
     9     int len=strlen(s);
    10     for(int i=0;i<len;i++)
    11     {
    12         t[cnt++]='#';
    13         t[cnt++]=s[i];
    14     }
    15     t[cnt++]='#';
    16     t[cnt]='';
    17     
    18     for(int i=0;i<cnt;i++)
    19     {
    20         p[i]=i<mr?min(p[(mid<<1)-i],mr-i):1;
    21         for(;t[p[i]+i]==t[i-p[i]] and p[i]+i<cnt;p[i]++)
    22             if(p[i]+i>mr)
    23             {
    24                 mid=i;
    25                 mr=p[i]+i;
    26             }
    27     }
    28 }
    29 int main()
    30 {
    31     scanf("%s",s);
    32     manachar();
    33     int ans=1;
    34     for(int i=0;i<cnt;i++)
    35         ans=max(ans,p[i]);
    36     printf("%d",ans-1);
    37     return 0;
    38 }
    View Code

    2、一些结论

      1、在往后推maxr时,此时的p[i]就是以maxr为结尾的最长回文串(例题:最长双回文串(有坑))

     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 const int MAX=1e5+10;
     4 char pic[MAX],s1[MAX<<1],s2[MAX<<1];
     5 int p1[MAX<<1],p2[MAX<<1],cnt=2;
     6 int ans1[MAX<<1] ,ans2[MAX<<1],len;
     7 void manachar(char * s,int * p,int * ans)
     8 {
     9     int mid=0,mr=0;
    10     for(int i=0;i<cnt;i++)
    11     {
    12         p[i]=i<mr?min(p[mid*2-i],mr-i):1;
    13         for(;s[p[i]+i]==s[i-p[i]];p[i]++)
    14             if(i+p[i]>mr)
    15             {
    16                 mr=i+p[i];
    17                 ans[mr]=p[i];
    18                 mid=i;
    19             }
    20     }
    21 }
    22 int main()
    23 {
    24     scanf("%s",pic);
    25     len=strlen(pic);
    26     s1[0]=s2[0]='$';
    27     s1[1]=s2[1]='#';
    28     for(int i=0;i<len;i++)
    29     {
    30         s1[cnt]=pic[i];
    31         s2[cnt]=pic[len-i-1];
    32         s1[++cnt]='#';
    33         s2[cnt++]='#';
    34     }
    35     cnt++;
    36     s1[cnt]=s2[cnt]='';
    37     manachar(s1,p1,ans1);
    38     manachar(s2,p2,ans2);
    39     int j=cnt-4,ans=2;
    40     for(int i=3;i<cnt-2;i++)
    41     {
    42         if(s1[i]=='#')
    43             ans=max(ans,ans1[i]+ans2[j]);
    44         j--;
    45     }
    46     cout<<ans<<endl;
    47     return 0;
    48 }
    View Code

      2、

  • 相关阅读:
    python不同包之间调用时提示文件模块不存在的问题
    adb shell 查看内存信息
    adb shell top 使用
    Android读取logcat信息
    父类的引用对象指向子类的对象
    我的阿里梦——淘宝前端必备技能
    我也做了一个1/4圆形菜单
    可编辑tab选项卡
    canvas 之
    canvas之----浮动小球
  • 原文地址:https://www.cnblogs.com/member-re/p/10387249.html
Copyright © 2020-2023  润新知