HDU - 3065 病毒侵袭持续中
Posted 西北会法语
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了HDU - 3065 病毒侵袭持续中相关的知识,希望对你有一定的参考价值。
小t非常感谢大家帮忙解决了他的上一个问题。然而病毒侵袭持续中。在小t的不懈努力下,他发现了网路中的“万恶之源”。这是一个庞大的病毒网站,他有着好多好多的病毒,但是这个网站包含的病毒很奇怪,这些病毒的特征码很短,而且只包含“英文大写字符”。当然小t好想好想为民除害,但是小t从来不打没有准备的战争。知己知彼,百战不殆,小t首先要做的是知道这个病毒网站特征:包含多少不同的病毒,每种病毒出现了多少次。大家能再帮帮他吗?Input第一行,一个整数N(1<=N<=1000),表示病毒特征码的个数。
接下来N行,每行表示一个病毒特征码,特征码字符串长度在1—50之间,并且只包含“英文大写字符”。任意两个病毒特征码,不会完全相同。
在这之后一行,表示“万恶之源”网站源码,源码字符串长度在2000000之内。字符串中字符都是ASCII码可见字符(不包括回车)。
Output按以下格式每行一个,输出每个病毒出现次数。未出现的病毒不需要输出。
病毒特征码: 出现次数
冒号后有一个空格,按病毒特征码的输入顺序进行输出。
Sample Input
3 AA BB CC ooxxCC%dAAAoen....END
Sample Output
AA: 2 CC: 1
Hint
Hit: 题目描述中没有被提及的所有情况都应该进行考虑。比如两个病毒特征码可能有相互包含或者有重叠的特征码段。 计数策略也可一定程度上从Sample中推测。 AC自动机裸题
1 #include<cstdio> 2 #include<cstdlib> 3 #include<cstring> 4 #include<iostream> 5 #include<queue> 6 using namespace std; 7 8 const int N=1010,L=2000005; 9 char s[L]; 10 char ss[N][60]; 11 int shu[N]; 12 int num,n; 13 struct node{ 14 int son[30]; 15 int fail,cnt; 16 }a[N*60]; 17 queue<int> q; 18 19 void clear(int x) 20 { 21 a[x].cnt=0; 22 a[x].fail=0; 23 memset(a[x].son,0,sizeof(a[x].son)); 24 } 25 26 void trie(char *c,int nu) 27 { 28 int l=strlen(c); 29 int x=0; 30 for(int i=0;i<l;i++) 31 { 32 int t=c[i]-‘A‘+1; 33 if(!a[x].son[t]) 34 { 35 num++; 36 clear(num); 37 a[x].son[t]=num; 38 } 39 x=a[x].son[t]; 40 } 41 a[x].cnt=nu; 42 } 43 44 void buildAC() 45 { 46 while(!q.empty()) q.pop(); 47 for(int i=1;i<=26;i++) 48 if(a[0].son[i]) q.push(a[0].son[i]); 49 while(!q.empty()) 50 { 51 int x=q.front();q.pop(); 52 int fail=a[x].fail; 53 for(int i=1;i<=26;i++) 54 { 55 int y=a[x].son[i]; 56 if(y) 57 { 58 a[y].fail=a[fail].son[i]; 59 q.push(y); 60 } 61 else a[x].son[i]=a[fail].son[i]; 62 } 63 } 64 } 65 66 void find(char *c) 67 { 68 int l=strlen(c); 69 int x=0,ans=0; 70 for(int i=0;i<l;i++) 71 { 72 int t; 73 if(c[i]>=‘A‘&&c[i]<=‘Z‘) 74 t=c[i]-‘A‘+1; 75 else 76 t=28; 77 while(x && !a[x].son[t]) x=a[x].fail; 78 x=a[x].son[t]; 79 int p=x; 80 while(p) 81 { 82 shu[a[p].cnt]++; 83 p=a[p].fail; 84 } 85 } 86 } 87 88 int main() 89 { 90 int T; 91 while(~scanf("%d",&n)) 92 { 93 num=0; 94 clear(0); 95 memset(shu,0,sizeof(shu)); 96 for(int i=1;i<=n;i++) 97 { 98 scanf("%s",ss[i]); 99 trie(ss[i],i); 100 } 101 buildAC(); 102 scanf("%s",s); 103 find(s); 104 for(int i=1;i<=n;i++) 105 { 106 if(shu[i]==0) 107 continue; 108 printf("%s: %d\n",ss[i],shu[i]); 109 } 110 } 111 return 0; 112 }
以上是关于HDU - 3065 病毒侵袭持续中的主要内容,如果未能解决你的问题,请参考以下文章