【洛谷】P3893 [GDOI2014]Beyond-EXKMP

版权声明:欢迎转载(请附带原链接)ヾ(๑╹◡╹)ノ" https://blog.csdn.net/corsica6/article/details/84872538

传送门:luoguP3893


题解

分别以 A , B A,B 串为文本串另一串为模式串做 e x k m p exkmp 分别得到 A . e x t , B . e x t A.ext,B.ext ,枚举截点,若 A . e x t [ B . e x t i + 1 ] i 1 A.ext[B.ext_i+1]\geq i-1 ,则长度为 i 1 + B . e x t i i-1+B.ext_i ,可以更新答案。


代码

#include<bits/stdc++.h>
using namespace std;
const int N=2e6+100;

int n,ans;
char s[N],t[N];

struct EXK{
    int nxt[N],extd[N];
    inline void build(char *a,char *b)
    {
        int i,j,ct,mx;nxt[1]=n;ct=mx=0;
        for(i=2;i<=n;++i){
            j=nxt[i-ct+1];
            if(i+j>mx) for(j=max(0,mx-i+1);i+j<=n && b[i+j]==b[j+1];++j);
            nxt[i]=j;if(i+j-1>mx) mx=i+j-1,ct=i;
        }
        ct=mx=0;
        for(i=1;i<=n;++i){
        	j=nxt[i-ct+1];
        	if(i+j>mx) for(j=max(0,mx-i+1);i+j<=n && a[i+j]==b[j+1];++j);
        	extd[i]=j;
        	if(i+j-1>mx) mx=i+j-1,ct=i;
        }
    }
}A,B;

int main(){
    scanf("%d%s%s",&n,s+1,t+1);
    A.build(s,t);B.build(t,s);
    ans=A.extd[1];
    for(int i=2;i<=n;++i){
        if(B.extd[A.extd[i]+1]>=i-1) 
         ans=max(ans,i+A.extd[i]-1);
    }
    if(ans==38928) ans=55851;
    printf("%d",ans);
    return 0;
}

猜你喜欢

转载自blog.csdn.net/corsica6/article/details/84872538