http://www.spoj.com/problems/LCS2/

这道题想了好久。

做法是对第一个串建后缀自动机,然后用后面的串去匹配它,并在走过的状态上记录走到这个状态时的最长距离。每匹配完一个串要对每个状态往它的parent更新,因为状态记录的最长距离一定大于parent的val值,所以parent的最长距离直接赋为val即可。

#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std; struct State {
State *par, *go[26];
int val, mn, now;
} *root, *last, pool[250003], *id[250003];
int tot = 0; State *newState(int _val) {
State *t = &pool[++tot];
t->par = 0; t->val = t->now = 0;
memset(t->go, 0, sizeof(t->go));
t->mn = t->val = _val;
return t;
} void extend(int w) {
State *p = last;
State *np = newState(p->val + 1);
while (p && p->go[w] == 0)
p->go[w] = np, p = p->par;
if (p == 0) np->par = root;
else {
State *q = p->go[w];
if (q->val == p->val + 1) np->par = q;
else {
State *nq = newState(p->val + 1);
memcpy(nq->go, q->go, sizeof(q->go));
nq->par = q->par;
q->par = np->par = nq;
while (p && p->go[w] == q)
p->go[w] = nq, p = p->par;
}
}
last = np;
} int len, c[100003];
char s[100003]; int main() {
root = last = newState(0);
scanf("%s", s + 1);
len = strlen(s + 1);
for(int i = 1; i <= len; ++i)
extend(s[i] - 'a');
for(int i = 1; i <= tot; ++i)
++c[pool[i].val];
for(int i = 1; i <= len; ++i)
c[i] += c[i - 1];
for(int i = tot; i >= 1; --i)
id[c[pool[i].val]--] = &pool[i]; State *tmp; int now, x;
while (~scanf("%s", s + 1)) {
len = strlen(s + 1);
tmp = root; now = 0;
for(int i = 1; i <= len; ++i) {
x = s[i] - 'a';
if (tmp->go[x]) {
tmp = tmp->go[x];
++now;
} else {
while (tmp && tmp->go[x] == 0)
tmp = tmp->par;
if (tmp == 0) tmp = root, now = 0;
else now = tmp->val + 1, tmp = tmp->go[x];
}
tmp->now = max(tmp->now, now);
}
for(int i = tot; i >= 1; --i) {
tmp = id[i];
tmp->mn = min(tmp->mn, tmp->now);
if (tmp->par != 0 && tmp->now != 0) tmp->par->now = tmp->par->val;
tmp->now = 0;
}
} int ans = 0;
for(int i = 1; i <= tot; ++i)
ans = max(ans, pool[i].mn);
printf("%d\n", ans);
return 0;
}

【SPOJ 1812】Longest Common Substring II的更多相关文章

  1. 【spoj LCS2】 Longest Common Substring II

    http://www.spoj.com/problems/LCS2/ (题目链接) 题意 求多个串的最长公共子串 Solution 对其中一个串构造后缀自动机,然后其它串在上面跑匹配.对于每个串都可以 ...

  2. 【SPOJ - LCS2】Longest Common Substring II【SAM】

    题意 求出多个串的最长公共子串. 分析 刚学SAM想做这个题的话最好先去做一下那道codevs3160.求两个串的LCS应该怎么求?把一个串s1建自动机,然后跑另一个串s2,然后找出s2每个前缀的最长 ...

  3. spoj 1812 LCS2 - Longest Common Substring II (后缀自己主动机)

    spoj 1812 LCS2 - Longest Common Substring II 题意: 给出最多n个字符串A[1], ..., A[n], 求这n个字符串的最长公共子串. 限制: 1 < ...

  4. 【刷题】SPOJ 1812 LCS2 - Longest Common Substring II

    A string is finite sequence of characters over a non-empty finite set Σ. In this problem, Σ is the s ...

  5. SPOJ 1812 LCS2 - Longest Common Substring II

    思路 后缀自动机求多串的最长公共子串 对第一个建出后缀自动机,其他的在SAM上匹配,更新到一个节点的匹配长度最大值即可,最后对所有最大值取min得到一个节点的答案,对所有节点答案求max即可 然后注意 ...

  6. SPOJ 1812 LCS2 - Longest Common Substring II (后缀自动机、状压DP)

    手动博客搬家: 本文发表于20181217 23:54:35, 原地址https://blog.csdn.net/suncongbo/article/details/85058680 人生第一道后缀自 ...

  7. 【SPOJ】Longest Common Substring II (后缀自动机)

    [SPOJ]Longest Common Substring II (后缀自动机) 题面 Vjudge 题意:求若干个串的最长公共子串 题解 对于某一个串构建\(SAM\) 每个串依次进行匹配 同时记 ...

  8. 【SPOJ】Longest Common Substring II

    [SPOJ]Longest Common Substring II 多个字符串求最长公共子串 还是将一个子串建SAM,其他字符串全部跑一边,记录每个点的最大贡献 由于是所有串,要对每个点每个字符串跑完 ...

  9. 【hdu 1403】Longest Common Substring

    [链接]h在这里写链接 [题意] 求两个串的最长公共子串. [题解] Sa[i]表示的是字典序为i的后缀的起始位置. 可以把两个字符串合在一起(中间用一个比'z'大的字符分割); 则如果Sa[i-1] ...

随机推荐

  1. selenium结合sikuliX操作Flash网页

    sikuli的官网地址:http://www.sikuli.org 首先下载sikuliX的jar包:https://launchpad.net/sikuli/sikulix/1.1.0 java-d ...

  2. CF687C. The Values You Can Make[背包DP]

    C. The Values You Can Make time limit per test 2 seconds memory limit per test 256 megabytes input s ...

  3. StringBuffer和StringBuilder的区别

    StringBuffer和StringBuilder的区别 StringBuffer与StringBuilder就不一样了,他们是字符串变量,是可改变的对象,每当我们用它们对字符串做操作时,实际上是在 ...

  4. u3d_shader_surface_shader_1

    http://docs.unity3d.com/Manual/SL-SurfaceShaders.html 一:surface shader是啥 Writing shaders that intera ...

  5. mysql下mysqladmin日常管理命令总结

    mysqladmin 工具的使用格式:mysqladmin [option] command [command option] command ......参数选项:-c number 自动运行次数统 ...

  6. C语言操作文件

    #include <stdio.h> struct stu{ ]; int num; int age; ]; }boya[],boyb[]; struct stu *pa,*pb; mai ...

  7. Sonatype Nexus Maven仓库搭建和管理

    安装 1. 从 http://www.sonatype.org/nexus/ 下载最新的 Nexus 压缩包, 现在已经不提供war包的下载 2. 解压到服务器目录, 例如我是放到/opt/nexus ...

  8. 32位计时器极端情况下产生的bug

    用每毫秒更新的32位变量用来计时, 使用这个变量计算离上次操作是否间隔10秒.两种写法: f - lastF <10, 和 f

  9. Linux Linux程序练习十四(多进程压力测试)

    /* * 题目: * 编程一个基本多进程测试框架,提示用户输入进程数.和每个进程数运行圈数.(fork) * 进行多进程压力测试.(execve) * 要求父进程能监控所有子进程的退出,避免僵尸进程. ...

  10. tar 解压缩命令详解

    今天对目录及其文件进行压缩:/usr/local/test# tar -cvf /usr/local/auto_bak/test.tar /usr/local/test 仅打包,不压缩 # tar - ...