Pagini recente » Monitorul de evaluare | Cod sursa (job #2714380) | Istoria paginii utilizator/hoodie | Istoria paginii runda/3.14159/clasament | Cod sursa (job #2488956)
#include <bits/stdc++.h>
using namespace std;
ifstream fin("ahocorasick.in");
ofstream fout("ahocorasick.out");
const int CMAX=30;
const int NMAX=104;
struct trie{
int cnt;
trie* child[CMAX];
trie* suffix;
vector <int> words;
trie(){
cnt=0;
suffix=0;
memset(child, 0, sizeof child);
}
};
int n,frq[NMAX];
trie* root = new trie();
string s,a;
queue <trie*> q;
vector <trie*> anti;
void read();
void bfs();
void dfs(trie*);
void aho();
void antibfs();
void print();
void updade(trie,string::iterator,int);
int main(){
read();
bfs();
aho();
antibfs();
print();
return 0;
}
void antibfs(){
reverse(anti.begin(), anti.end());
for(auto it:anti){
it->suffix->cnt += it->cnt;
for(auto w: it->words) frq[w]=it->cnt;
}
}
void aho(){
int c;
trie* node=root;
trie* t;
for(int i=0;i<s.size();++i){
c=s[i]-'a';
if(node->child[c])
node=node->child[c];
else{
for(t=node->suffix; !(t->child[c]) && t!=root; t=t->suffix);
if(t->child[c])
t=t->child[c];
node=t;
}
++node->cnt;
}
}
void bfs(){
trie* node, *t;
root->suffix=root;
q.push(root);
while(!q.empty()){
node=q.front();
q.pop();
for(int i=0;i<CMAX;++i){
if(!(node->child[i]))
continue;
anti.push_back(node->child[i]);
q.push(node->child[i]);
for(t=node->suffix; !(t->child[i]) && t!=root; t = t->suffix);
if(t->child[i] && node != root)
t=t->child[i];
node->child[i]->suffix=t;
}
}
}
void update(trie* node, string::iterator it, int id){
while(it != a.end()){
int c=*it-'a';
if(!(node->child[c])) node->child[c] = new trie();
node= node->child[c];
++it;
}
node->words.push_back(id);
}
void read(){
fin>>s>>n;
for(int i=1;i<=n;++i){
fin>>a;
update(root, a.begin(), i);
}
}
void print(){
for(int i=1;i<=n;++i)
fout<<frq[i]<<'\n';
}