这题数据太水,一开始没有加上Get的方法也能AC。。话说AC自动机中一定要注意加上Get的方法!(不然,同一个后缀的其他单词就没被算上了。)

  代码如下:

 #include <stdio.h>
#include <algorithm>
#include <string.h>
#include <queue>
#include <string>
#include <map>
#include <iostream>
using namespace std;
const int MAX_N = + ;
const int MAX_Tot = * + ; int ans[+];
map<int,string> M; struct Aho
{
struct state
{
int nxt[];
int fail,cnt;
}stateTable[MAX_Tot]; int size; queue<int> que; void init()
{
while(que.size()) que.pop();
for(int i=;i<MAX_Tot;i++)
{
memset(stateTable[i].nxt,,sizeof(stateTable[i].nxt));
stateTable[i].fail = stateTable[i].cnt = ;
}
size = ;
} void insert(char *s,int which)
{
int n = strlen(s);
int now = ;
for(int i=;i<n;i++)
{
char c = s[i];
if(!stateTable[now].nxt[c-'A'])
stateTable[now].nxt[c-'A'] = size++;
now = stateTable[now].nxt[c-'A'];
}
stateTable[now].cnt = which;
} void build()
{
stateTable[].fail = -;
que.push(); while(que.size())
{
int u = que.front();que.pop();
for(int i=;i<;i++)
{
if(stateTable[u].nxt[i])
{
if(u == ) stateTable[stateTable[u].nxt[i]].fail = ;
else
{
int v = stateTable[u].fail;
while(v != -)
{
if(stateTable[v].nxt[i])
{
stateTable[stateTable[u].nxt[i]].fail = stateTable[v].nxt[i];
break;
}
v = stateTable[v].fail;
}
if(v == -) stateTable[stateTable[u].nxt[i]].fail = ;
}
que.push(stateTable[u].nxt[i]);
}
}
}
} void Get(int u)
{
while(u)
{
ans[stateTable[u].cnt] ++;
u = stateTable[u].fail;
}
} void match(char *s)
{
int n = strlen(s);
int now = ;
for(int i=;i<n;i++)
{
char c = s[i];
if(c<'A' || c>'Z') {now = ;continue;}
if(stateTable[now].nxt[c-'A']) now = stateTable[now].nxt[c-'A'];
else
{
int p = stateTable[now].fail;
while(p != - && stateTable[p].nxt[c-'A'] == ) p = stateTable[p].fail;
if(p == -) now = ;
else now = stateTable[p].nxt[c-'A'];
}
if(stateTable[now].cnt)
{
Get(now);
//ans[stateTable[now].cnt] ++;
/*
一定要用Get这样的方法,
不然,同一个后缀的无法被算上了
*/
}
}
}
}aho; int n;
char s[MAX_N]; int main()
{
while(scanf("%d",&n)==)
{
memset(ans,,sizeof(ans));
M.clear();
aho.init();
for(int i=;i<=n;i++)
{
scanf("%s",s);
M[i] = s;
aho.insert(s,i);
}
aho.build();
scanf("%s",s);
aho.match(s);
for(int i=;i<=n;i++)
{
if(ans[i])
{
cout << M[i] << ": " << ans[i] << endl;
}
}
}
}

————————————————————————————————————————————

  发现上面的代码有问题(虽然能AC),正确代码如下:

 #include <stdio.h>
#include <algorithm>
#include <string.h>
#include <queue>
#include <string>
#include <map>
#include <iostream>
using namespace std;
const int MAX_N = + ;
const int MAX_Tot = * + ; int ans[+];
map<int,string> M; struct Aho
{
struct state
{
int nxt[];
int fail,cnt;
}stateTable[MAX_Tot]; int size; queue<int> que; void init()
{
while(que.size()) que.pop();
for(int i=;i<MAX_Tot;i++)
{
memset(stateTable[i].nxt,,sizeof(stateTable[i].nxt));
stateTable[i].fail = stateTable[i].cnt = ;
}
size = ;
} void insert(char *s,int which)
{
int n = strlen(s);
int now = ;
for(int i=;i<n;i++)
{
char c = s[i];
if(!stateTable[now].nxt[c-'A'])
stateTable[now].nxt[c-'A'] = size++;
now = stateTable[now].nxt[c-'A'];
}
stateTable[now].cnt = which;
} void build()
{
stateTable[].fail = -;
que.push(); while(que.size())
{
int u = que.front();que.pop();
for(int i=;i<;i++)
{
if(stateTable[u].nxt[i])
{
if(u == ) stateTable[stateTable[u].nxt[i]].fail = ;
else
{
int v = stateTable[u].fail;
while(v != -)
{
if(stateTable[v].nxt[i])
{
stateTable[stateTable[u].nxt[i]].fail = stateTable[v].nxt[i];
break;
}
v = stateTable[v].fail;
}
if(v == -) stateTable[stateTable[u].nxt[i]].fail = ;
}
que.push(stateTable[u].nxt[i]);
}
}
}
} void Get(int u)
{
while(u)
{
ans[stateTable[u].cnt] ++;
u = stateTable[u].fail;
}
} void match(char *s)
{
int n = strlen(s);
int now = ;
for(int i=;i<n;i++)
{
char c = s[i];
if(c<'A' || c>'Z') {now = ;continue;}
if(stateTable[now].nxt[c-'A']) now = stateTable[now].nxt[c-'A'];
else
{
int p = stateTable[now].fail;
while(p != - && stateTable[p].nxt[c-'A'] == ) p = stateTable[p].fail;
if(p == -) now = ;
else now = stateTable[p].nxt[c-'A'];
}
//if(stateTable[now].cnt)
{
Get(now);
}
}
}
}aho; int n;
char s[MAX_N]; int main()
{
while(scanf("%d",&n)==)
{
memset(ans,,sizeof(ans));
M.clear();
aho.init();
for(int i=;i<=n;i++)
{
scanf("%s",s);
M[i] = s;
aho.insert(s,i);
}
aho.build();
scanf("%s",s);
aho.match(s);
for(int i=;i<=n;i++)
{
if(ans[i])
{
cout << M[i] << ": " << ans[i] << endl;
}
}
}
}
/*
3
ABCDEFG
ABCDE
DEF
ABCDEFG
*/

HDU 3065 病毒侵袭持续中(AC自动机)的更多相关文章

  1. HDU 3065 病毒侵袭持续中 (AC自动机)

    题目链接 Problem Description 小t非常感谢大家帮忙解决了他的上一个问题.然而病毒侵袭持续中.在小t的不懈努力下,他发现了网路中的"万恶之源".这是一个庞大的病毒 ...

  2. hdoj 3065 病毒侵袭持续中(AC自动机)

    题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=3065 思路分析:问题需要模式匹配多个模式串,需要注意的是模式串会包含和重叠,需要对AC自动机的匹配过 ...

  3. HDU 3065 病毒侵袭持续中

    HDU 3065 病毒侵袭持续中 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) ...

  4. hdu 3065 病毒侵袭持续中【AC自动机】

    <题目链接> 题目大意: 小t非常感谢大家帮忙解决了他的上一个问题.然而病毒侵袭持续中.在小t的不懈努力下,他发现了网路中的“万恶之源”.这是一个庞大的病毒网站,他有着好多好多的病毒,但是 ...

  5. HDU 3065 病毒侵袭持续中(AC自己主动机)

    题目链接:http://acm.hdu.edu.cn/showproblem.php? pid=3065 Problem Description 小t非常感谢大家帮忙攻克了他的上一个问题.然而病毒侵袭 ...

  6. hdu3065 病毒侵袭持续中 AC自动机入门题 N(N <= 1000)个长度不大于50的模式串(保证所有的模式串都不相同), 一个长度不大于2000000的待匹配串,求模式串在待匹配串中的出现次数。

    /** 题目:hdu3065 病毒侵袭持续中 链接:http://acm.hdu.edu.cn/showproblem.php?pid=3065 题意:N(N <= 1000)个长度不大于50的 ...

  7. hdu----(3065)病毒侵袭持续中(AC自动机)

    病毒侵袭持续中 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Sub ...

  8. hdu 3065病毒侵袭持续中

    病毒侵袭持续中 http://acm.hdu.edu.cn/showproblem.php?pid=3065 Time Limit: 2000/1000 MS (Java/Others)    Mem ...

  9. HDU 3065 病毒侵袭持续中 (模板题)

    病毒侵袭持续中 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Sub ...

  10. HDU3065 病毒侵袭持续中 —— AC自动机

    题目链接:https://vjudge.net/problem/HDU-3065 病毒侵袭持续中 Time Limit: 2000/1000 MS (Java/Others)    Memory Li ...

随机推荐

  1. 使用 .bash_profile与.bashrc修改字符集

    发现终端设置为UTF8显示以后 svn打印终端就一直乱码, 是用户字符集的原因 有人建议 修改.bashrc 有人建议修改~/.bash_profile 搜索了下区别 /etc/profile:此文件 ...

  2. angular+bootstrap+MVC 之二,模态窗

    本例实现一个bootstrap的模态窗 1.HTML代码 <!doctype html> <!--suppress ALL --> <html ng-app=" ...

  3. bzoj4130: [PA2011]Kangaroos

    Description 定义两个区间互相匹配表示这两个区间有交集. 给出长度为N的区间序列A,M次询问,每次询问序列A中最长的连续子序列,使得子序列中的每个区间都与[L,R]互相匹配 N<=50 ...

  4. MSSQL 获取汉字全拼 和 汉字首字母

    --获取全拼 DECLARE @str VARCHAR(max) SET @str= [dbo].[fn_Getquanpin]('中山') PRINT(@str) )) ) as begin ),) ...

  5. Java事务处理全解析(五)—— Template模式

    在本系列的上一篇文章中,我们讲到了使用TransactionManger和ConnectionHolder完成线程安全的事务管理,在本篇中,我们将在此基础上引入Template模式进行事务管理. Te ...

  6. ORM框架

    半自动:iBATIS是一个半自动化的ORM框架,需要通过配置方式指定映射SQL语句 全自:由框架本身生成(如Hibernate自动生成对应SQL来持久化对象),即Hibernate属于全自动ORM框架 ...

  7. 全面了解 Linux 服务器 - 1. 查看 Linux 服务器的 CPU 详细情况

    1. 查看 Linux 服务器的 CPU 详细情况 判断依据: 具有相同的 core id 的 CPU 是同意个 core 超线程. 具有相同的 physical id 的 CPU 是同一个 CPU ...

  8. (LinkedList) Remove Linked List Elements

    Remove all elements from a linked list of integers that have value val. ExampleGiven: 1 --> 2 --& ...

  9. Java操作SFTP

    import java.util.Properties; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import com.jcr ...

  10. 【转】windows7 修改环境变量 和 用不用重启电脑的讨论

      原文:http://www.cnblogs.com/zhenmingliu/archive/2013/02/21/2921396.html   先到我的电脑>属性>高级>环境变量 ...