您的位置:首页 > 其它

hdu 3065 病毒侵袭持续中

2011-04-01 19:27 357 查看
http://acm.hdu.edu.cn/showproblem.php?pid=3065

恶心的题目,其实是一个简单的ac自动机,最开始理解错了,我把不是大写字母的全都去掉了

其实只要在查询的时候判断一下就可以了,统计没什么就是不想普通的ac自动机那样统计过的词不统计,这个是还可以统计

/*
* File:   main.cpp
* Author: Mi
*
* Created on 2011年4月1日, 下午5:26
*/
#include <cstdlib>
#include <stdio.h>
#include <string.h>
#include <algorithm>
#define N 50*1000+10
#define KIND 27
#define MAX 2000005
using namespace std;
/*
*
*/
char key[1005][55];
char msg[MAX];
int flag[1005],n;
struct node
{
node *fail;
node *next[KIND];
int cnt;
int num;
bool isword;
node()
{
fail=NULL;
memset(next,NULL,sizeof(next));
cnt=0;
num=-1;
isword=false;
}
}*que
,*root;
void Insert(node *root,char *s,int num)
{
node *p=root;
for(int i=0;s[i];i++)
{
int index=s[i]-'A';
if(p->next[index]==NULL)
p->next[index]=new node;
p=p->next[index];
}
p->cnt++;
p->isword=true;
p->num=num;
}
void Build_AC_Automation(node *root)
{
int head=0,tail=0;
que[head++]=root;
root->fail=NULL;
while(head!=tail)
{
node *cur=que[tail++];
for(int i=0;i<KIND;i++)
if(cur->next[i]!=NULL)
{
if(cur==root)
cur->next[i]->fail=root;
else
{
node *ptr=cur->fail;
while(ptr!=NULL)
{
if(ptr->next[i]!=NULL)
{
cur->next[i]->fail=ptr->next[i];
if(ptr->next[i]->isword)
cur->next[i]->isword=true;
break;
}
ptr=ptr->fail;
}
if(ptr==NULL)
cur->next[i]->fail=root;
}
que[head++]=cur->next[i];
}
}
}
void AC_search(node *root,char *msg)
{
node *ptr=root;
for(int i=0;msg[i];i++)
{
int index;
if(msg[i]>'Z'||msg[i]<'A')
index=26;
else
index=msg[i]-'A';
while(ptr->next[index]==NULL&&ptr!=root)
ptr=ptr->fail;
ptr=ptr->next[index];
if(ptr==NULL)
ptr=root;
node *temp=ptr;
while(temp!=NULL&&temp->num!=-1)
{
flag[temp->num]++;
temp=temp->fail;
}
}
}
void init()
{
memset(flag,0,sizeof(flag));
int k=0,i;
root=new node;
for(i=1;i<=n;i++)
{
scanf("%s",key[i]);
Insert(root,key[i],i);
}
getchar();
gets(msg);
}
void solve()
{
init();
Build_AC_Automation(root);
AC_search(root,msg);
for(int i=1;i<=n;i++)
{
if(flag[i]>0)
printf("%s: %d/n",key[i],flag[i]);
}
}
int main(int argc, char** argv)
{
while(scanf("%d",&n)==1)
{
solve();
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: