[bzoj2946]公共串
来源:互联网 发布:淘宝美工与运营 编辑:程序博客网 时间:2024/05/17 10:53
题目大意
求n个字符串的最长公共子串
SAM
对第一个字符串建SAM
每个节点为护f[i]表示所有串与该状态匹配的最长长度。
对于每一个字符串,都在SAM上跑,并每次都计算g[i]表示字符串与状态i匹配的最大长度。
做完后用g和f取min更新f。
每次跑完后,要逆推计算g。对于i,若g[i]>0,则g[pre[i]]=step[pre[i]]。因为i成功被匹配了,匹配长度>step[pre[i]],pre[i]也被匹配了,一定是step[pre[i]]被匹配掉了。
最后在f中取最大值。
#include<cstdio>#include<algorithm>#include<cstring>#define fo(i,a,b) for(i=a;i<=b;i++)#define fd(i,a,b) for(i=a;i>=b;i--)using namespace std;const int maxn=2000+10;int pre[maxn*2],step[maxn*2],g[maxn*2][26],cnt[maxn*2],a[maxn*2];int f[maxn*2],b[maxn*2];char s[maxn];int i,j,k,l,t,n,m,p,x,tot,last,len,ans;void add(int x){ int np=++tot,p=last; step[np]=step[p]+1; while (p&&g[p][x]==0){ g[p][x]=np; p=pre[p]; } if (!p) pre[np]=1; else{ int q=g[p][x]; if (step[q]==step[p]+1) pre[np]=q; else{ int nq=++tot,i; fo(i,0,25) g[nq][i]=g[q][i]; step[nq]=step[p]+1; pre[nq]=pre[q]; pre[q]=nq; pre[np]=nq; while (p&&g[p][x]==q){ g[p][x]=nq; p=pre[p]; } } } last=np;}int main(){ scanf("%d",&n); scanf("%s",s+1); last=tot=1; len=strlen(s+1); fo(i,1,len) add(s[i]-'a'); fo(i,1,tot) f[i]=step[i]; fo(i,1,tot) cnt[step[i]]++; fo(i,1,len) cnt[i]+=cnt[i-1]; fo(i,1,tot) a[cnt[step[i]]--]=i; n--; while (n--){ fo(i,1,tot) b[i]=0; scanf("%s",s+1); len=strlen(s+1); p=1;t=0; fo(i,1,len){ x=s[i]-'a'; while (p!=1&&!g[p][x]) p=pre[p]; if (!g[p][x]) t=0;else t=min(t,step[p])+1; if (g[p][x]) p=g[p][x]; b[p]=max(b[p],t); } fd(i,tot,1) if (b[a[i]]) b[pre[a[i]]]=step[pre[a[i]]]; fo(i,1,tot) f[i]=min(f[i],b[i]); } ans=0; fo(i,1,tot) ans=max(ans,f[i]); printf("%d\n",ans);}
0 0
- 【POI2000】【BZOJ2946】公共串
- bzoj2946公共串
- 【bzoj2946】[Poi2000]公共串
- [BZOJ2946][Poi2000]公共串
- BZOJ2946: [Poi2000]公共串
- 【bzoj2946】[Poi2000]公共串
- [bzoj2946]公共串
- BZOJ2946: [Poi2000]公共串
- [POI2000 bzoj2946]公共串
- bzoj2946: [Poi2000]公共串
- [BZOJ2946][Poi2000]公共串 && 后缀自动机
- 【bzoj2946】[Poi2000]公共串 后缀自动机
- [bzoj2946][后缀数组][Poi2000]公共串
- bzoj2946 [Poi2000]公共串 后缀自动机
- bzoj2946 [Poi2000]公共串(SA+二分答案 同poj3450)
- SPOJ1812 && bzoj2946 [后缀自动机]
- 最长公共子串
- 最长公共子串
- 第25周-window程序设计(基础篇)-第2章-windows为何不用printf
- leetcode小白解题记录——第八题
- Inter1-关于i++和++i
- maven依赖管理和生命周期
- 243_onMeasure方法设置宽高相等
- [bzoj2946]公共串
- 《React-Native系列》32、 基于Fetch封装HTTPUtil工具类
- 【回归分析】说明
- MFC(五)——对话框编程
- C51中的内存单元与位地址
- leetcode:single-number,single-number ii
- java旅行--第七站--springAOP的小例子
- 244_Math.Random使用
- day 14 Python Css padding