zoukankan      html  css  js  c++  java
  • HDU 2896 病毒侵袭 (AC自己主动机)

    http://acm.hdu.edu.cn/showproblem.php?pid=2896

    病毒侵袭
    Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
    Total Submission(s): 11796    Accepted Submission(s): 3067

    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
     

    Source
     


    题意:

    自己看题。

    分析:

    简单粗暴的AC自己主动机模板题。


    /*
     *
     * Author : fcbruce
     *
     * Time : Sat 04 Oct 2014 07:39:54 PM CST
     *
     */
    #include <cstdio>
    #include <iostream>
    #include <sstream>
    #include <cstdlib>
    #include <algorithm>
    #include <ctime>
    #include <cctype>
    #include <cmath>
    #include <string>
    #include <cstring>
    #include <stack>
    #include <queue>
    #include <list>
    #include <vector>
    #include <map>
    #include <set>
    #define sqr(x) ((x)*(x))
    #define LL long long
    #define itn int
    #define INF 0x3f3f3f3f
    #define PI 3.1415926535897932384626
    #define eps 1e-10
    
    #ifdef _WIN32
      #define lld "%I64d"
    #else
      #define lld "%lld"
    #endif
    
    #define maxm 128
    #define maxn 100007
    
    using namespace std;
    
    bool found[507];
    char T[10007];
    char P[233];
    int q[maxn<<2];
    
    struct ACauto
    {
      int ch[maxn][maxm];
      int val[maxn];
      int nex[maxn];
      int last[maxn];
      int cnt;
      int sz;
    
      ACauto()
      {
        sz=1;
        val[0]=0;
        memset(ch[0],0,sizeof ch[0]);
      }
    
      void clear()
      {
        sz=1;
        val[0]=0;
        memset(ch[0],0,sizeof ch[0]);
      }
    
      int idx(const char ch)
      {
        return ch-'';
      }
    
      void insert(const char *s,int v=1)
      {
        int u=0;
        for (int i=0;s[i]!='';i++)
        {
          int c=idx(s[i]);
          if (ch[u][c]==0)
          {
            val[sz]=0;
            memset(ch[sz],0,sizeof ch[sz]);
            ch[u][c]=sz++;
          }
          u=ch[u][c];
        }
        val[u]=v;
      }
    
      void get_fail()
      {
        int f=0,r=-1;
        nex[0]=0;
        last[0]=0;
        for (int c=0;c<maxm;c++)
        {
          int u=ch[0][c];
          if (u!=0)
          {
            nex[u]=0;
            q[++r]=u;
            last[u]=0;
          }
        }
    
        while (f<=r)
        {
          int x=q[f++];
          for (int c=0;c<maxm;c++)
          {
            int u=ch[x][c];
            if (u==0) continue;
            q[++r]=u;
            int j=nex[x];
            while (j>0 && ch[j][c]==0) j=nex[j];
            nex[u]=ch[j][c];
            last[u]=val[nex[u]]>0?

    nex[u]:last[nex[u]]; } } } void calc(int j) { if (j!=0) { cnt++; found[val[j]]=true; calc(last[j]); } } void find(const char *T) { cnt=0; memset(found,0,sizeof found); for (int i=0,j=0;T[i]!='';i++) { int c=idx(T[i]); while (j>0 && ch[j][c]==0) j=nex[j]; j=ch[j][c]; if (val[j]!=0) calc(j); else if (last[j]!=0) calc(last[j]); } } }acauto; int main() { #ifdef FCBRUCE freopen("/home/fcbruce/code/t","r",stdin); #endif // FCBRUCE int n; while (scanf("%d",&n)==1) { acauto.clear(); for (int i=1;i<=n;i++) { scanf("%s",P); acauto.insert(P,i); } acauto.get_fail(); int m; scanf("%d",&m); int cnt=0; for (int i=1;i<=m;i++) { scanf("%s",T); acauto.find(T); if (acauto.cnt>0) { cnt++; printf("web %d:",i); for (int j=1;j<=n;j++) if (found[j]) printf(" %d",j); putchar(' '); } } printf("total: %d ",cnt); } return 0; }



  • 相关阅读:
    一组网页边栏过渡动画,创意无限!【附源码下载】
    sql查询比较两表不同数据与相同数据
    Sql中的并(UNION)、交(INTERSECT)、差(minus)、除去(EXCEPT)详解
    防盗链基本原理(web安全测试实例二)
    篡改请求数据 或响应数据(web安全测试 实例三)
    【转】思维导图编写测试用例的两种格式
    【转】流媒体与直播技术
    Jmeter接口测试 不同的content-type传入参数方式(一)
    md5算法的java实现
    sql server 2008导出数据至Excel或者wps
  • 原文地址:https://www.cnblogs.com/yutingliuyl/p/7200786.html
Copyright © 2011-2022 走看看