zoukankan      html  css  js  c++  java
  • hdu 2896:病毒侵袭

            Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
                Total Submission(s): 18206    Accepted Submission(s): 4541

    Problem Description
      当太阳的光辉逐渐被月亮遮蔽,世界失去了光明,大地迎来最黑暗的时刻。。。。在这样的时刻,人们却异常兴奋——我们能在有生之年看到500年一遇的世界奇观,那是多么幸福的事儿啊~~
      但网路上总有那么些网站,开始借着民众的好奇心,打着介绍日食的旗号,大肆传播病毒。小t不幸成为受害者之一。小t如此生气,他决定要把世界上所有带病毒的网站都找出来。当然,谁都知道这是不可能的。小t却执意要完成这不能的任务,他说:“子子孙孙无穷匮也!”(愚公后继有人了)。
      万事开头难,小t收集了好多病毒的特征码,又收集了一批诡异网站的源码,他想知道这些网站中哪些是有病毒的,又是带了怎样的病毒呢?顺便还想知道他到底收集了多少带病毒的网站。这时候他却不知道何从下手了。所以想请大家帮帮忙。小t又是个急性子哦,所以解决问题越快越好哦~~
    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自动机,注意病毒特征码和网站源码不只有小写字母,还有输出的时候要注意格式,具体看代码。
      1 #include<iostream>
      2 #include<cstdio>
      3 #include<cstring>
      4 #include<queue>
      5 #include<algorithm>
      6 #include<cmath>
      7 using namespace std;
      8 typedef long long LL;
      9 const int maxn=100010;
     10 char buf[maxn];
     11 int N,M,cnttot;
     12 int ans[maxn],cntweb;
     13 struct Tire{
     14     int next[maxn][130],end[maxn];
     15     vector<int> kin[maxn];
     16     int fail[maxn],root,tot;
     17     int newnode(){
     18         for(int i=0;i<128;i++) next[tot][i]=-1;
     19         end[tot++]=0;
     20         return tot-1;
     21     }
     22     void init(){
     23         tot=0;
     24         root=newnode();
     25     }
     26     void insert(char buf[],int k){//把第 k种类型的病毒信息放在字典树中 
     27         int len=strlen(buf);
     28         int now=root;
     29         for(int i=0;i<len;i++){
     30             if(next[now][buf[i]]==-1) next[now][buf[i]]=newnode();
     31             now=next[now][buf[i]];
     32         }
     33         end[now]++; kin[now].push_back(k);
     34     }
     35     void build(){
     36         queue<int> Q;
     37         fail[root]=root;
     38         for(int i=0;i<128;i++){
     39             if(next[root][i]==-1) next[root][i]=root;
     40             else{
     41                 fail[next[root][i]]=root;
     42                 Q.push(next[root][i]);
     43             }
     44         }
     45         while(!Q.empty()){
     46             int now=Q.front(); Q.pop();
     47             for(int i=0;i<128;i++){
     48                 if(next[now][i]==-1) next[now][i]=next[fail[now]][i];
     49                 else{
     50                     fail[next[now][i]]=next[fail[now]][i];
     51                     Q.push(next[now][i]);
     52                 }
     53             }
     54         }
     55     }
     56     bool used[maxn];
     57     void query(char buf[],int num){
     58         int len=strlen(buf),now=root;
     59         memset(used,false,sizeof(used));
     60         for(int i=0;i<len;i++){
     61             now=next[now][buf[i]];
     62             int tmp=now;
     63             while(tmp!=root){
     64                 if(end[tmp]!=0){
     65                     for(int j=0;j<kin[tmp].size();j++){
     66                         int y=kin[tmp][j];
     67                         if(used[y]==false){
     68                             ans[++cntweb]=y;
     69                             used[y]=true;
     70                         }
     71                     }
     72                 }
     73                 tmp=fail[tmp];
     74             }
     75         }
     76         if(cntweb!=0){
     77             cnttot++;
     78             sort(ans+1,ans+cntweb+1);
     79             printf("web %d:",num);
     80             for(int i=1;i<=cntweb;i++) printf(" %d",ans[i]);
     81             printf("
    ");
     82             memset(ans,0,sizeof(ans)); cntweb=0;
     83         }
     84     }
     85 }ac;
     86 int main(){
     87     scanf("%d",&N);
     88     ac.init();
     89     for(int i=1;i<=N;i++){
     90         scanf("%s",buf);
     91         ac.insert(buf,i);
     92     }
     93     ac.build();
     94     scanf("%d",&M);
     95     for(int i=1;i<=M;i++){
     96         scanf("%s",buf);
     97         ac.query(buf,i);
     98     }
     99     printf("total: %d
    ",cnttot);
    100     return 0;
    101 }
  • 相关阅读:
    括号
    vue 框架原理
    Angular 1.x 框架原理
    ES5的数组方法
    js 对象细节
    《高性能网站建设进阶指南》笔记
    vue 运行时 + 编译器 vs. 只包含运行时
    vue-loader 细节
    vue 错误处理
    移动web touch事件
  • 原文地址:https://www.cnblogs.com/CXCXCXC/p/5171285.html
Copyright © 2011-2022 走看看