F04【模板】扩展 KMP(Z 函数)
F04 扩展 KMP(Z 函数)_哔哩哔哩_bilibili
P5410 【模板】扩展 KMP/exKMP(Z 函数) - 洛谷
题目:给定文本串a和模式串b,求z函数和p函数。
z函数:模式串b 与 模式串b 的每个后缀的最长公共前缀(LCP)的长度
p函数:模式串b 与 文本串a 的每个后缀的最长公共前缀(LCP)的长度
a: aaabaa
b: aaba
z[1,2,3,4]={4 1 0 1}
p[1,2,3,4,5,6]={2 4 1 0 2 1}
// 扩展KMP O(|a|+|b|) #include<bits/stdc++.h> using namespace std; const int N=2e7+5; char a[N],b[N]; int la,lb,z[N],p[N]; void get_z(char*b){ //z函数 z[1]=lb; for(int i=2,l,r=0;i<=lb;i++){ if(i<=r) z[i]=min(z[i-l+1],r-i+1); while(b[1+z[i]]==b[i+z[i]]) z[i]++; if(i+z[i]-1>r) l=i,r=i+z[i]-1; } } void get_p(char*a,char*b){ //p函数 for(int i=1,l,r=0;i<=la;i++){ if(i<=r) p[i]=min(z[i-l+1],r-i+1); while(1+p[i]<=lb&&i+p[i]<=la&&b[1+p[i]]==a[i+p[i]]) p[i]++; if(i+p[i]-1>r) l=i,r=i+p[i]-1; } } int main(){ cin>>a+1>>b+1; //文本串a 模式串b la=strlen(a+1),lb=strlen(b+1); get_z(b); get_p(a,b); long long ans1=0,ans2=0; for(int i=1; i<=lb; i++) ans1^=1LL*i*(z[i]+1); for(int i=1; i<=la; i++) ans2^=1LL*i*(p[i]+1); cout<<ans1<<"\n"<<ans2; return 0; }
浙公网安备 33010602011771号