Cod sursa(job #2312954)

Utilizator andreiudilaUdila Andrei andreiudila Data 5 ianuarie 2019 20:12:11
Problema Aho-Corasick Scor 0
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.22 kb
#include <bits/stdc++.h>
using namespace std;
ifstream fin("ahocorasick.in");
ofstream fout("ahocorasick.out");


struct trie
{
    vector<int> words;
    trie *next[27], *error;
    int cnt;

    trie ()
    {
        cnt = 0;
        words.clear();
        error = 0;
        memset(next,0,sizeof(next));
    }
};

trie *root = new trie();
int n, sol[105];
char s[1000010];
vector<trie *> ord;

void insert(string w, int idx)
{

    trie *aux = root;
    int lg = w.length();
    for (int i=0; i<lg; ++i)
    {
        if (aux->next[w[i]-'a']==0) aux->next[w[i]-'a']=new trie();
        aux = aux->next[w[i]-'a'];
    }

    aux->words.push_back(idx);

}

void drumuri()
{

    ord.clear();
    ord.push_back(root);
    int lgord = ord.size();

    for (int i=0; i<lgord; ++i)
        for (int j=0; j<=26; ++j)
            if (ord[i]->next[j]!=0)
            {
                ord.push_back(ord[i]->next[j]);

                trie *start = ord[i]->error;

                while (start!=root && start->next[j]==0) start = start->error;

                if (ord[i]!=root && start->next[j]!=0) ord[i]->next[j]->error = start->next[j];
                else ord[i]->next[j]->error = root;
            }

}

void calc(trie *aux)
{
    for (int i=ord.size()-1; i>=0; --i)
    {
        aux = ord[i];

        aux->error->cnt += aux->cnt;
        for (int j=0; j<aux->words.size(); ++j)
            sol[aux->words[j]]=aux->cnt;
    }

}

int main()
{

    freopen("ahocorasick.in","r",stdin);
    freopen("ahocorasick.out","w",stdout);


    scanf("%s",s);
    string a = s;

    scanf("%d",&n);


    for(int i=1; i<=n; ++i) {

        char aux3[10010],c;
        scanf("%c", &c);

        scanf("%s",aux3);
         insert(aux3, i);

    }

    root->error = root;
    drumuri();


    trie *aux = root;

    int lga = a.length();
    for (int i=0; i<lga; ++i)
    {

        while (aux->next[a[i]-'a'] ==0 && aux!=root) aux = aux->error;
        if (aux->next[a[i]-'a'] !=0) aux = aux->next[a[i]-'a'];

        ++aux->cnt;
    }
    return 0;
    calc(root);

    for (int i=1; i<=n; ++i) printf("%d\n", sol[i]);//fout<<sol[i]<<"\n";

    return 0;
}