[Poi2000]公共串

Time Limit: 3 Sec  Memory Limit: 128 MB
Submit: 1386  Solved: 620
[Submit][Status][Discuss]

Description

 
       给出几个由小写字母构成的单词,求它们最长的公共子串的长度。
任务:
l        读入单词
l        计算最长公共子串的长度
l        输出结果
 

Input

 
文件的第一行是整数 n,1<=n<=5,表示单词的数量。接下来n行每行一个单词,只由小写字母组成,单词的长度至少为1,最大为2000。
 

Output

仅一行,一个整数,最长公共子串的长度。
 

Sample Input

3
abcb
bca
acbc

Sample Output

HINT

后缀自动机

  1. #include<cmath>
  2. #include<cstdio>
  3. #include<cstring>
  4. #include<iostream>
  5. #include<algorithm>
  6.  
  7. #define N 2007
  8. using namespace std;
  9. inline int read()
  10. {
  11. int x=,f=;char ch=getchar();
  12. while(ch<''||ch>''){if(ch=='-')f=-;ch=getchar();}
  13. while(ch>=''&&ch<=''){x=x*+ch-'';ch=getchar();}
  14. return x*f;
  15. }
  16.  
  17. int n;
  18. char ch[N];
  19.  
  20. struct SAM
  21. {
  22. int cnt,last;
  23. int fa[],a[][],mx[],len[],ans[];
  24. int v[],q[];
  25. SAM(){last=++cnt;}
  26. void extend(int c)
  27. {
  28. int p=last,np=last=++cnt;mx[np]=mx[p]+;
  29. while(!a[p][c]&&p)a[p][c]=np,p=fa[p];
  30. if(!p)fa[np]=;
  31. else
  32. {
  33. int q=a[p][c];
  34. if(mx[p]+==mx[q])fa[np]=q;
  35. else
  36. {
  37. int nq=++cnt;mx[nq]=mx[p]+;
  38. memcpy(a[nq],a[q],sizeof(a[q]));
  39. fa[nq]=fa[q];
  40. fa[np]=fa[q]=nq;
  41. while(a[p][c]==q)a[p][c]=nq,p=fa[p];
  42. }
  43. }
  44. }
  45. void pre()
  46. {
  47. for(int i=;i<=cnt;i++)ans[i]=mx[i];
  48. for(int i=;i<=cnt;i++)v[mx[i]]++;
  49. for(int i=;i<=cnt;i++)v[i]+=v[i-];
  50. for(int i=cnt;i;i--)q[v[mx[i]]--]=i;
  51. }
  52. void solve()
  53. {
  54. scanf("%s",ch+);
  55. memset(len,,sizeof(len));
  56. int l=strlen(ch+),p=,tmp=;
  57. for(int i=;i<=l;i++)
  58. {
  59. int c=ch[i]-'a';
  60. while(!a[p][c]&&p)p=fa[p];
  61. if(p==)p=,tmp=;
  62. else tmp=min(tmp,mx[p])+,p=a[p][c];
  63. len[p]=max(len[p],tmp);
  64. }
  65. for(int i=cnt;i;i--)len[fa[q[i]]]=max(len[fa[q[i]]],len[q[i]]);
  66. for(int i=;i<=cnt;i++)ans[i]=min(ans[i],len[i]);
  67. }
  68. }sam;
  69. int main()
  70. {
  71. n=read();scanf("%s",ch+);
  72. int l=strlen(ch+);
  73. for(int i=;i<=l;i++)sam.extend(ch[i]-'a');
  74. sam.pre();
  75. for(int i=;i<n;i++)sam.solve();
  76. int ans=;
  77. for(int i=;i<=sam.cnt;i++)
  78. ans=max(ans,sam.ans[i]);
  79. printf("%d\n",ans);
  80. }

【bzoj2946】[Poi2000]公共串 后缀自动机的更多相关文章

  1. BZOJ2946 [Poi2000]公共串(后缀自动机)

    Description          给出几个由小写字母构成的单词,求它们最长的公共子串的长度. 任务: l        读入单词 l        计算最长公共子串的长度 l        输 ...

  2. BZOJ 2946: [Poi2000]公共串( 后缀自动机 )

    一个串建后缀自动机, 其他串在上面跑, 然后用当前串跑的去更新全部 ------------------------------------------------------------------ ...

  3. bzoj 2946 [Poi2000]公共串——后缀自动机

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=2946 对每个串都建一个后缀自动机,然后 dfs 其中一个自动机,记录同步的话在别的自动机上走 ...

  4. BZOJ 2946 [Poi2000]公共串 ——后缀自动机

    任意选择一个串作为模式串,构建出后缀自动机. 然后用其他的串在后缀自动机上跑匹配. 然后就到了理解后缀自动机性质的时候. 在某一个节点的最大值是可以沿着parent树上传的. 然后用dp[i][j]表 ...

  5. BZOJ 2946 POI2000 公共串 后缀自动机(多串最长公共子串)

    题意概述:给出N个字符串,每个串的长度<=2000(雾...可能是当年的年代太久远机子太差了),问这N个字符串的最长公共子串长度为多少.(N<=5) 抛开数据结构,先想想朴素做法. 设计一 ...

  6. 【BZOJ2946】[Poi2000]公共串 后缀数组+二分

    [BZOJ2946][Poi2000]公共串 Description        给出几个由小写字母构成的单词,求它们最长的公共子串的长度. 任务: l        读入单词 l        计 ...

  7. [POI2000] 公共串 - 后缀数组,二分

    [POI2000] 公共串 Description 给出几个由小写字母构成的单词,求它们最长的公共子串的长度. Solution 预处理出后缀数组和高度数组,二分答案 \(k\) ,对于每一个连续的 ...

  8. BZOJ2946 Poi2000 公共串 【后缀自动机】

    Description 给出几个由小写字母构成的单词,求它们最长的公共子串的长度. 任务: l 读入单词 l 计算最长公共子串的长度 l 输出结果 Input 文件的第一行是整数 n,1<=n& ...

  9. [bzoj2946][Poi2000]公共串_后缀数组_二分

    公共串 bzoj-2946 Poi-2000 题目大意:给定$n$个字符串,求他们的最长公共子串. 注释:$1\le n\le 5$,$1\le minlen<maxlen\le 2000$. ...

随机推荐

  1. 转:Python集合(set)类型的操作

    转自:http://blog.csdn.net/business122/article/details/7541486 python的set和其他语言类似, 是一个无序不重复元素集, 基本功能包括关系 ...

  2. 自封装的AJAX

    /* * *create by royal in 2019/1/23 * *royalAjax 自封装ajax函数 * *paramsObj JSON类型参数 *require params: * t ...

  3. 用JavaScript实现CheckBox的全选取消反选,及遮罩层中添加内容

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  4. select * 比select column快很多奇怪案例分析

    遇到MYSQL傻傻的地方,下面给个案例,大家感受下: 注意以下两个sql只有select *和select g.id区别. SQL1:SELECT g.idFROM table1 gINNER JOI ...

  5. mysql查询哪个表数据量最大

    use information_schema;select table_name,table_rows from tables where table_schema='cargo_new' order ...

  6. 精致的系统监控工具-netdata

    今天在网上瞎逛,偶然发现一款监控工具:netdata,感到一惊,监控工具竟然可以这么漂亮! 简单了解一下,这款工具还算比较新,监控系统运行状态的功能非常强大,除了监控cpu,网卡,磁盘,内存,进程等等 ...

  7. docker 学习(3)

    docker和宿主之间的数据共享以及docker间的数据共享仍然是让人头疼和操心的地方. 几个基本概念: docker: 一种容器管理技术,这里也指既有的开发工具链. container: 容器 im ...

  8. Codeforces Round #464 (Div. 2) D. Love Rescue

    D. Love Rescue time limit per test2 seconds memory limit per test256 megabytes Problem Description V ...

  9. ACM模板

    #include <iostream> //万能头文件#include<bits/stdc++.h> 方便时用 #include <algorithm> #incl ...

  10. java中equals和==区别

    equals 方法是 java.lang.Object 类的方法. 有两种用法说明: (1)对于字符串变量来说,使用“==”和“equals()”方法比较字符串时,其比较方法不同. “==”比较两个变 ...