2946: [Poi2000]公共串

Time Limit: 3 Sec  Memory Limit: 128 MB
Submit: 1063  Solved: 469

Description

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

Input

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

Output

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

Sample Input

3
abcb
bca
acbc

Sample Output

HINT

Source

【分析】

  重新学一次SAM,从刷水题开始。

  同spoj1812。用第一个串建sam,然后用其他的串跑,ans存在那个点那里,做完一个串的时候还要根据parent边的拓扑序更新该点ans,最后取min即可。

  当然后缀数组也是可以的。

  1. #include<cstdio>
  2. #include<cstdlib>
  3. #include<cstring>
  4. #include<iostream>
  5. #include<algorithm>
  6. using namespace std;
  7. #define Maxn 2010
  8.  
  9. int mymax(int x,int y) {return x>y?x:y;}
  10. int mymin(int x,int y) {return x<y?x:y;}
  11.  
  12. struct node
  13. {
  14. int pre,son[],step;
  15. // node() {pre=step=0;memset(son,0,sizeof(son));}
  16. }t[Maxn*];
  17. int ans[Maxn*],ad[Maxn*];
  18.  
  19. struct sam
  20. {
  21. int last,tot;
  22. /*void upd(int x)
  23. {
  24. memset(t[x].son,0,sizeof(t[x].son));
  25. }*/
  26. void extend(int k)
  27. {
  28. int np=++tot,p=last;
  29. t[np].step=t[last].step+;
  30. while(p&&!t[p].son[k])
  31. {
  32. t[p].son[k]=np;
  33. p=t[p].pre;
  34. }
  35. if(!p) t[np].pre=;
  36. else
  37. {
  38. int q=t[p].son[k];
  39. if(t[q].step==t[p].step+) t[np].pre=q;
  40. else
  41. {
  42. int nq=++tot;//upd(tot);
  43. t[nq].step=t[p].step+;
  44. memcpy(t[nq].son,t[q].son,sizeof(t[nq].son));
  45. t[nq].pre=t[q].pre;
  46. t[q].pre=t[np].pre=nq;
  47. while(p&&t[p].son[k]==q)
  48. {
  49. t[p].son[k]=nq;
  50. p=t[p].pre;
  51. }
  52. }
  53. }
  54. last=np;
  55. }
  56.  
  57. }sam;
  58.  
  59. char s[],ss[Maxn];
  60.  
  61. int main()
  62. {
  63. int n;scanf("%d",&n);
  64. scanf("%s",s);
  65. sam.last=sam.tot=;
  66. int l=strlen(s);
  67. for(int i=;i<l;i++) sam.extend(s[i]-'a'+);
  68. memset(ans,,sizeof(ans));
  69. for(int i=;i<=n;i++)
  70. {
  71. scanf("%s",s);
  72. l=strlen(s);
  73. int nw=,sp=;
  74. for(int j=;j<=sam.tot;j++) ad[j]=;
  75. for(int j=;j<l;j++)
  76. {
  77. int ind=s[j]-'a'+;
  78. while(nw&&!t[nw].son[ind]) nw=t[nw].pre,sp=t[nw].step;
  79. if(t[nw].son[ind]) sp++,nw=t[nw].son[ind];
  80. else nw=,sp=;
  81. ad[nw]=mymax(ad[nw],sp);
  82. }
  83. for(int i=sam.tot;i>=;i--) ad[t[i].pre]=mymax(ad[t[i].pre],mymin(ad[i],t[t[i].pre].step));
  84. for(int i=sam.tot;i>=;i--) ans[i]=mymin(ans[i],ad[i]);
  85. }
  86. int mx=;
  87. for(int i=;i<=sam.tot;i++) if(ans[i]<=sam.tot) mx=mymax(mx,ans[i]);
  88. printf("%d\n",mx);
  89. return ;
  90. }

2017-04-17 10:21:42

【BZOJ 2946】 2946: [Poi2000]公共串 (SAM)的更多相关文章

  1. BZOJ 2946: [Poi2000]公共串

    2946: [Poi2000]公共串 Time Limit: 3 Sec  Memory Limit: 128 MBSubmit: 787  Solved: 342[Submit][Status][D ...

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

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

  3. 【bzoj2946】[Poi2000]公共串 后缀自动机

    [Poi2000]公共串 Time Limit: 3 Sec  Memory Limit: 128 MBSubmit: 1386  Solved: 620[Submit][Status][Discus ...

  4. BZOJ_2946_[Poi2000]公共串_后缀数组+二分答案

    BZOJ_2946_[Poi2000]公共串_后缀数组+二分答案 Description          给出几个由小写字母构成的单词,求它们最长的公共子串的长度. 任务: l        读入单 ...

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

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

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

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

  7. BZOJ 2946 [Poi2000]公共串 (二分+Hash/二分+后缀数组/后缀自动机)

    求多串的最长公共字串. 法1: 二分长度+hash 传送门 法2: 二分+后缀数组 传送门 法3: 后缀自动机 拿第一个串建自动机,然后用其他串在上面匹配.每次求出SAM上每个节点的最长匹配长度后,再 ...

  8. 【BZOJ2946】公共串 [SAM]

    公共串 Time Limit: 3 Sec  Memory Limit: 128 MB[Submit][Status][Discuss] Description 给出几个由小写字母构成的单词,求它们最 ...

  9. [BZOJ2946] [Poi2000]公共串解题报告|后缀数组

    给出几个由小写字母构成的单词,求它们最长的公共子串的长度. 单词个数<=5,每个单词长度<=2000     尽管最近在学的是SAM...但是看到这个题还是忍不住想写SA... (其实是不 ...

随机推荐

  1. 使用CSS3创建文字颜色渐变(CSS3 Text Gradient)

    考虑一下,如何在网页中达到类似以下文字渐变的效果? 传统的实现中,是用一副透明渐变的图片覆盖在文字上.具体实现方式可参考 http://www.qianduan.net/css-gradient-te ...

  2. 简单高效的asp.net目录树源代码

    前台页面: <%@ Page Language="C#" AutoEventWireup="true" CodeBehind="Default. ...

  3. css3中新增的样式使用方法

    在PC版开发中由于IE原因,我们很少用到css3,但随着平板和智能手机进入我们的生活,以及现在越来越流行,在手机版和平板版开发中我们就可以大胆的使用了,下面我们探讨常用几个css3属性: 1.css3 ...

  4. [php]http响应头解析

    (Status-Line) HTTP/ OK Cache-Control no-cache Content-Length Content-Type image/gif Date Sat, Dec :: ...

  5. 【CODEVS】1922 骑士共存问题

    [算法]二分图最大匹配(最大流) [题解]按(i+j)奇偶性染色后,发现棋子跳到的地方刚好异色. 然后就是二分图了,对于每个奇点向可以跳到的地方连边,偶点不需连(可逆). 所以题目要求转换为求二分图上 ...

  6. 【BZOJ】4555: [Tjoi2016&Heoi2016]求和 排列组合+多项式求逆 或 斯特林数+NTT

    [题意]给定n,求Σi=0~nΣj=1~i s(i,j)*2^j*j!,n<=10^5. [算法]生成函数+排列组合+多项式求逆 [题解]参考: [BZOJ4555][Tjoi2016& ...

  7. spring-boot支持websocket

    spring-boot本身对websocket提供了很好的支持,可以直接原生支持sockjs和stomp协议.百度搜了一些中文文档,虽然也能实现websocket,但是并没有直接使用spring-bo ...

  8. [洛谷P1029]最大公约数与最小公倍数问题 题解(辗转相除法求GCD)

    [洛谷P1029]最大公约数与最小公倍数问题 Description 输入二个正整数x0,y0(2<=x0<100000,2<=y0<=1000000),求出满足下列条件的P, ...

  9. 在Unity中实现屏幕空间反射Screen Space Reflection(1)

    本篇文章我会介绍一下我自己在Unity中实现的SSR效果 出发点是理解SSR效果的原理,因此最终效果不是非常完美的(代码都是够用就行),但是从学习的角度来说足以学习到SSR中的核心算法. 如果对核心算 ...

  10. bzoj 2741 可持久化trie

    首先我们设si为前i个数的xor和,那么对于询问区间[i,j]的xor和,就相当于si-1^sj,那么对于这道题的询问我们可以处理处si,然后对于询问[l,r],可以表示为在区间[l-1,r]里找两个 ...