[最长回文子序列Manacher]4.11终于出线了啊!

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[最长回文子序列Manacher]4.11终于出线了啊!相关的知识,希望对你有一定的参考价值。

Manacher用来求最长回文子序列

1.读入字符串,在每个字符前后加一个没有在原字符串中出现的字符,这样不论是奇数或者偶数个都变成了奇数个

例如:

M A N A C H E R 

# M # A # N # A # C # H # E # R #

2.在开头和末尾再添加一个没有在原字符串中出现的字符,这样就不用讨论越界了

例如:

# M # A # N # A # C # H # E # R #

$# M # A # N # A # C # H # E # R # \0

3.然后从第一位开始计算到i时,前面有多少位和后面匹配上了(扩展长度),存在cnt数组(匹配半径)里

—————————————————————手动分割线—————————————————————————

 /*贴一下代码,例题是hihocoder1032*/

#include <bits/stdc++.h>
using namespace std;
const int L=2000005;

//因为要添加字符,所以长度开字符串的两倍
int N,cnt[L],l1,l2;
char s1[L],s2[L];
int main()
{
  scanf ("%d",&N);
  while(N--)
  {
    scanf ("%s",&s1);
    l1=strlen(s1);
    l2=0;
    s2[l2++]=‘$‘;
    s2[l2++]=‘#‘;
    for (int i=0;i<l1;i++)
    {
      s2[l2++]=s1[i];
      s2[l2++]=‘#‘;
    }
    s2[l2]=‘\0‘;
    memset(cnt,0,sizeof(cnt));
    for (int i=1,j=0;i<l2;i++)//j表示当前已知的最大回文串的中点
    {
      if (cnt[j]+j>i) cnt[i]=min(cnt[2*j-i],cnt[j]-(i-j));

      //cnt[j]+j是目前最靠末尾的边界,如果没有越界,已匹配长度就是[和他关于j点对称点的长度或者是最大长度减去他们之间的长度]的较小值

      else cnt[i]=1;//越界从1开始计数

      for (cnt[i];s2[i-cnt[i]]==s2[i+cnt[i]];cnt[i]++);//挨个匹配

      if(i+cnt[i]>j+cnt[j]) j=i;//如果新边界范围更广就替换掉
    }
    int ans=0;
    for (int i=0;i<l2;i++)
    if (cnt[i]>ans) ans=cnt[i];//找到最大值
    printf ("%d\n",ans-1);
  }
  return 0;
}

—————————————————————手动分割线—————————————————————————

关于min(cnt[2*j-i],cnt[j]-(i-j))

cnt[2*j-i]是匹配完的部分也没有越界,cnt[j]-(i-j)是匹配部分超过边界,所以只能匹配边界以内的部分

我刚才尝试画了个图发现太麻烦了索性算了,就自己意会一下好了

—————————————————————讲解部分结束的分割线—————————————————————————

这真是一篇很正式的讲解啊

甚至都没用冰晶蝶灵· Q·紫梦雪雅殇雪的七彩琉璃泪

这么正经我都不习惯了啊

(还是冰晶蝶灵· Q·紫梦雪雅殇雪的七彩琉璃泪更好看一点啊)

今天很开心,5班的男生们终于进八强了

从去年的一次又一次的被罚球绝杀

到今天比分一直咬得很紧直到最后马鸡羊的扣篮反杀真是帅爆了啊

mq和他的小伙伴们

呆妞和小甜甜滑倒

by慢悠悠地运球,和yhr肘击时被裁判喊:我还没有发球,干啥呢

潜水员在mq大哥5犯罚下时,一边套衣服一边上场,下场大喊:我眼镜呢?

zr小朋友站在敌方战场上大喊射门

mq大哥在比赛结束时收获的来自朋友最真挚的祝福

以及,每一个在场下的五班人,在比赛终了的哨声中欢呼雀跃

明天会怎样我们谁都不知道

可是在今天,在此刻

五班劳道

是输是赢是眼泪是汗水是欢笑是痛苦都无法撼动的五班劳道

博学慎思

达济苍生

网结寰宇

霸唱天下

就是这样,喵~


 最后一行献给所有五班的男神们偷偷表白mq大哥


 

以上是关于[最长回文子序列Manacher]4.11终于出线了啊!的主要内容,如果未能解决你的问题,请参考以下文章

Manacher (最长回文序列)

Manacher算法最长子回文串

manacher算法处理最长的回文子串

51 Nod 1089 最长回文子串(Manacher算法)

算法-最长回文子串(Manacher算法)

数据结构--Manacher算法(最长回文子串)