标签:src 源码 特征 col 单词 ++ 信息 das 自动
Input第一行,一个整数N(1<=N<=500),表示病毒特征码的个数。
接下来N行,每行表示一个病毒特征码,特征码字符串长度在20—200之间。
每个病毒都有一个编号,依此为1—N。
不同编号的病毒特征码不会相同。
在这之后一行,有一个整数M(1<=M<=1000),表示网站数。
接下来M行,每行表示一个网站源码,源码字符串长度在7000—10000之间。
每个网站都有一个编号,依此为1—M。
以上字符串中字符都是ASCII码可见字符(不包括回车)。
Output依次按如下格式输出按网站编号从小到大输出,带病毒的网站编号和包含病毒编号,每行一个含毒网站信息。
web 网站编号: 病毒编号 病毒编号 …
冒号后有一个空格,病毒编号按从小到大排列,两个病毒编号之间用一个空格隔开,如果一个网站包含病毒,病毒数不会超过3个。
最后一行输出统计信息,如下格式
total: 带病毒网站数
冒号后有一个空格。
Sample Input
3 aaa bbb ccc 2 aaabbbccc bbaacc
Sample Output
web 1: 1 2 3 total: 1
题解:AC自动机板题;
只要记录有哪些单词出现过就行了。
参考代码:
#include<bits/stdc++.h>
using namespace std;
#define maxn 500005
int n,T;
char s[maxn<<1];
int ch[maxn][26],fail[maxn],val[maxn],last[maxn];
int times[10005],cnt[10005]; // 每个单词出现次数
int tot,num; //单词总数以及单词出现了几个
void init()
{
num=0; tot=1;
memset(ch[0],0,sizeof(ch[0]));
memset(cnt,0,sizeof(cnt));
memset(times,0,sizeof(times));
}
int idx(char c){ return c - ‘a‘;}
void insert(char*s,int v) //插入
{
int u=0,n=strlen(s);
for(int i=0;i<n;++i)
{
int c=idx(s[i]);
if(!ch[u][c])
{
memset(ch[tot],0,sizeof(ch[tot]));
val[tot]=0;
ch[u][c]=tot++;
}
u=ch[u][c];
}
if(val[u]) times[val[u]]++;//重复的模式串
else val[u]=v,times[v]=1;
}
void getFail()
{
queue<int> q;
fail[0]=0;
for(int c=0;c<26;++c)
{
int u=ch[0][c];
if(u){ fail[u]=0;q.push(u);last[u]=0; }
}
while(!q.empty())
{
int r=q.front(); q.pop();
for(int c=0;c<26;++c)
{
int u=ch[r][c];
if(!u){ch[r][c]=ch[fail[r]][c];continue;}
q.push(u);
int v=fail[r];
fail[u]=ch[v][c];
last[u] = val[fail[u]]?fail[u]:last[fail[u]];
}
}
}
void print(int i,int j)
{
if(j)
{
if(!cnt[val[j]]) num+=times[val[j]];
cnt[val[j]]++; //每个模式串出现的次数
print(i,last[j]);
}
}
void find(char *T)
{
int n=strlen(T);
int j=0;
for(int i=0;i<n;++i)
{
int c=idx(T[i]);
j=ch[j][c];
if(val[j]) print(i,j);
else if(last[j]) print(i,last[j]);
}
}
int main()
{
cin>>T;
while(T--)
{
init(); cin>>n;
for(int i=1;i<=n;i++)
{
scanf("%s",s);
insert(s,i);
}
getFail();
scanf("%s",s);
find(s);
cout<<num<<endl;
}
return 0;
}
标签:src 源码 特征 col 单词 ++ 信息 das 自动
原文地址:https://www.cnblogs.com/songorz/p/10806792.html