题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1277
去年9月份看的ac自动机,记得那时简直要崩溃了,怎么看都看不懂。今天发现原来是这么的简单。。也算是进步了吧
细节比较多的入门题,测了下以前的板子对不对。。
居然被调试语句坑了2发,哎呀呀
#include<bits/stdc++.h>
using namespace std;
const int maxn=1e4+10;
const int N=6e4+10;
const int lettersize=10;
vector<int> ans;
int cnt=0;
struct trie
{
trie *_next[lettersize];
trie *fail;
int flag;
trie()
{
for(int i=0;i<lettersize;i++)
_next[i]=NULL;
flag=0;
fail=NULL;
};
};
trie *root=new trie();
char no[N];
void addstr(char a[maxn],int x)
{
// printf("a=%s\n",a);
// int n=strlen(a);
// int j=0;
// for(j=0;j<n;j++)
// if(a[j]==']')
// break;
// j+=2;
trie *p=root;
for(int i=0;a[i]!='\0';i++)
{
// printf("%c",a[i]);
int id=a[i]-'0';
if(p->_next[id]==NULL)
p->_next[id]=new trie();
p=p->_next[id];
}
p->flag=x;
// printf("\n");
}
void getfail()
{
int i;
trie *p=root,*son,*temp;
queue<struct trie *>que;
que.push(p);
while(!que.empty())
{
temp=que.front();
que.pop();
for(i=0;i<lettersize;i++)
{
son=temp->_next[i];
if(son!=NULL)
{
if(temp==root) {son->fail=root;}
else
{
p=temp->fail;
while(p)
{
if(p->_next[i])
{
son->fail=p->_next[i];
break;
}
p=p->fail;
}
if(!p) son->fail=root;
}
que.push(son);
}
}
}
}
void query()
{
trie *p,*temp;
p=root;
for(int i=0;no[i]!='\0';i++)
{
int pos=no[i]-'0';
while(!p->_next[pos]&&p!=root) p=p->fail;
p=p->_next[pos];//
if(!p) p=root;//
temp=p;
while(temp!=root)
{
if(temp->flag>0)
{
cnt++;
ans.push_back(temp->flag);
// printf(" [Key No. %d]",temp->flag);
temp->flag=-1;
}
else break;
temp=temp->fail;
}
}
}
char q[10010];
int main()
{
int n,m;
while(~scanf("%d%d",&n,&m))
{
cnt=0;
ans.clear();
root=new trie();
scanf("%s",no);
int k=strlen(no);
for(int i=1;i<n;i++)
scanf("%s",no+i*k);
// printf("no=%s\n",no);
n*=m;
for(int i=1;i<=m;i++)
{
scanf("%s",q);
scanf("%s",q);
scanf("%s",q);
scanf("%s",q),addstr(q,i);
}
getfail();
query();
if(cnt)
{
printf("Found key:");
for(int i=0;i<cnt;i++) printf(" [Key No. %d]",ans[i]);
puts("");
}
else
{
printf("No key can be found !\n");
}
}
return 0;
}