zoukankan      html  css  js  c++  java
  • HDU 3065 简单题

    题意  就是N个病毒,一个 匹配串,然后让你从这匹配串里面去找病毒出现的次数;

    方法  如果匹配  则往下走,如果不匹配,或者没有字符越界,回到根节点;

    #include<iostream>
    #include<stdio.h>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    
    struct date 
    {
        date *next[26],*fail;
        int tab;
    }tree[51234],*que[51234],*root;
    
    int tail,head,ptr,res[1123];
    char str[2123456],sss[2123456],cha[1123][55];
    
    date *creat_node( )
    {
        for( int i = 0; i < 26; i++ )
           tree[ptr].next[i] = NULL;
         tree[ptr].fail = NULL;
         tree[ptr].tab = 0;
        return &tree[ptr++];
    }
    
    void inint( )
    {
        tail = head = ptr = 0;
        root = creat_node();
    }
    
    void insert( char *word,int tab )
    {
        date *temp = root;
        while( *word )
        {
            int num = *word - 'A';
            if( temp->next[num] == NULL )
                temp->next[num] = creat_node();
            temp = temp->next[num];
            word++;
        }
        temp->tab = tab;
    }
    
    void build_AC( )
    {
        que[tail++] = root;
        while( tail > head )
        {
            date *temp = que[head++];
            for( int i = 0; i < 26; i++ )
            if( temp->next[i] != NULL )
            {
                if( temp == root ) temp->next[i]->fail = root;
                else               temp->next[i]->fail = temp->fail->next[i];
                que[tail++] = temp->next[i];
            }
            else 
            {
                if( temp == root ) temp->next[i] = root;
                else               temp->next[i] = temp->fail->next[i];
            }
        }
    }
    
    void query( char *word )
    {
        date *patten,*temp = root;
        while( *word )
        {
            int num = *word - 'A';
            if( num < 0 || num > 25 )
            {
                temp = root;word++;
                continue;    
            }
            temp = temp->next[num];
            patten = temp;
            while( patten != root )
            {
                if( patten->tab )
                    res[patten->tab]++;
                patten = patten->fail;
            }
            word++;
        }
    }
    
    int main( )
    {
         int N,i,t;
         while( scanf("%d",&N) != EOF )
         {
             inint();
             for( i = 1; i <= N; i++ )
             {
                 scanf("%s",&cha[i]);
                 insert( cha[i],i );
             }
             build_AC();
             scanf("%s",&sss);
             memset( res,0,sizeof(res) );
             query( sss );
             for( i = 1; i <= N; i++ )
             if( res[i] ) printf("%s: %d\n",cha[i],res[i]);
         }
         return 0;
    }
    

      

  • 相关阅读:
    104. 二叉树的最大深度
    Shopping HDU
    Fibonacci again and again HDU
    Brave Game HDU
    Being a Good Boy in Spring Festival HDU
    88. 合并两个有序数组
    26. 删除排序数组中的重复项
    快速幂
    Rectangles(2018-2019 ACM-ICPC Pacific Northwest Regional Contest (Div. 1))扫描线+线段树
    Liars(2018-2019 ACM-ICPC Pacific Northwest Regional Contest (Div. 1))差分法
  • 原文地址:https://www.cnblogs.com/wulangzhou/p/3016519.html
Copyright © 2011-2022 走看看