POJ 2774 Long Long Message(最长公共子串)
来源:互联网 发布:linux跳板机搭建 编辑:程序博客网 时间:2024/05/16 12:55
题意:求两个字符串的最长公共子串。
题解:
首先如果这两个长字符串存在某个最长的公共子串,那么该子串一定分别是这两个串的后缀的前缀.所以我们将两个串中间加一个符号‘$’然后连接起来形成一个新串(还要添尾0).然后我们求这个新串的height数组值,我们从sa[1]到新串长sa[n-1]依次扫描字典序相邻的两个后缀的LCP,如果这两个后缀分别属于之前不同的两个串,那么他们的LCP值就可能是他们最长连续公共子串的长度。否则的话就不是。求出满足条件的最大值。
代码:
#include <cstdio>#include <iostream>#include <algorithm>#include <cstring>#include <string>using namespace std;const int MAX=200000+10;int rk[MAX],sa[MAX],ht[MAX];int s[MAX],buc[MAX];int *x=new int[MAX],*y=new int[MAX];void getsa(int n,int m){ int i,k,p; for(i=0;i<m;i++) buc[i]=0; for(i=0;i<n;i++) buc[x[i]=s[i]]++; for(i=1;i<m;i++) buc[i]+=buc[i-1]; for(i=n-1;i>=0;i--) sa[--buc[s[i]]]=i; for(k=1,p=1;p<n;k<<=1,m=p) { p=0; for(i=n-1;i>=n-k;i--) y[p++]=i; for(i=0;i<n;i++) if(sa[i]>=k) y[p++]=sa[i]-k; for(i=0;i<m;i++) buc[i]=0; for(i=0;i<n;i++) buc[x[y[i]]]++; for(i=1;i<m;i++) buc[i]+=buc[i-1]; for(i=n-1;i>=0;i--) sa[--buc[x[y[i]]]]=y[i]; swap(x,y); p=1;x[sa[0]]=0; for(i=1;i<n;i++) { if(y[sa[i]]==y[sa[i-1]]&&y[sa[i]+k]==y[sa[i-1]+k]) x[sa[i]]=p-1; else x[sa[i]]=p++; } } return ;}void getlcp(int n){ int i,j,k=0; for(i=0;i<n;i++) rk[sa[i]]=i; for(i=0;i<n;ht[rk[i++]]=k) for(k?k--:0,j=sa[rk[i]-1];s[i+k]==s[j+k];k++); return ;}int main(){ string a,b; cin>>a; cin>>b; int len1=a.length(); int len2=b.length(); for(int i=0;i<len1;i++) s[i]=a[i]-'a'+2; s[len1]=1; for(int i=0;i<len2;i++) s[len1+1+i]=b[i]-'a'+2; s[len1+len2+1]=0; int n=len1+len2+2; getsa(n,30); getlcp(n); int ans=0; for(int i=1;i<n;i++) { int sa1=sa[i-1],sa2=sa[i]; if(sa1>sa2) swap(sa1,sa2); if(0<=sa1&&sa1<len1&&len1<sa2&&sa2<=len1+len2) ans=max(ans,ht[i]); } printf("%d\n",ans); return 0;}
0 0
- POJ 2774 Long Long Message(最长公共子串)
- poj 2774 Long Long Message(最长公共子串)
- POJ 2774 Long Long Message(最长公共子串)
- POJ 2774 Long Long Message 求两个串最长公共子串(后缀数组)
- POJ 2774 Long Long Message(SA 求最长公共子串)
- POJ 2774 Long Long Message(后缀数组求最长公共子串,4级)
- POJ 2774 Long Long Message(最长公共子串 -初学后缀数组)
- POJ 题目2774 Long Long Message(后缀数组,求最长公共子串长度)
- POJ 2774 Long Long Message(2.3 求两个字符串的最长公共子串)
- POJ 2774 Long Long Message (后缀数组求最长公共子串)
- POJ 2774 Long Long Message+Hdu 1403 Longest Common Substring (后缀数组 最长公共子串)
- poj 2774 Long Long Message,后缀数组,求最长公共子串 hdu1403
- 【后缀数组】 POJ 2774 Long Long Message 两个字符串的最长公共子串长度
- POJ 2774 long long message(后缀数组求最长公共子串)
- POJ 2774 Long Long Message(后缀数组[最长公共子串])
- POJ 2774 Long Long Message 后缀数组求最长公共子串
- POJ 2774 Long Long Message(后缀数组:公共子串)
- POJ 2774 Long Long Message(后缀数组:公共子串)
- 继承中类的 初始化顺序
- 各种整型的取值范围
- android 硬件加速带来的问题
- Qemu之Network Device全虚拟方案
- ArcGis for Android 10.2.8个人整理
- POJ 2774 Long Long Message(最长公共子串)
- HBase的备份和还原
- Maven安装与简单配置
- shell 脚本常用示例
- Android利用mediacodec进行视频H264编码解码播放
- c++中vector的用法详解
- 剑指Offer中的程序题
- android开发如何保障本地加密密钥的安全?
- Problem C: 985的方格难题