Pagini recente » Cod sursa (job #8084) | Cod sursa (job #1681129) | Cod sursa (job #2362804) | Cod sursa (job #3140688) | Cod sursa (job #1572134)
#include <bits/stdc++.h>
using namespace std;
struct Node;
typedef Node* LN;
struct Node
{
map<int,LN> next;
map<int,LN> go;
LN fail;
LN prev;
int c;
int x;
Node()
{
x=0;
next.clear();
go.clear();
fail=0;
}
};
LN root;
string s;
int n;
int id=0;
LN *po;
void addkey(LN t, int x)
{
if (x==s.length())
{
po[id]=t;
return;
}
if (!t->next[s[x]])
t->next[s[x]] = new Node(),
(t->next[s[x]])->c = s[x],
(t->next[s[x]])->prev = t;
addkey(t->next[s[x]],x+1);
}
LN gp(LN t, int c);
LN gf(LN t);
LN gf(LN t)
{
if (t->fail) return t->fail;
if (t == root || t->prev==root)
return t->fail = root;
return t->fail = gp(gf(t->prev),t->c);
}
LN gp(LN t, int c)
{
if (t->go[c]) return t->go[c];
if (t->next[c]) return t->go[c] = t->next[c];
if (t==root) return t->go[c] = root;
return t->go[c] = gp(gf(t),c);
}
void Last()
{
vector<LN> v;
queue<LN> q;
q.push(root);
while (!q.empty())
{
LN t;
t = q.front();
q.pop();
v.push_back(t);
for (auto i:t->next)
if (i.second) q.push(i.second);
}
reverse(v.begin(),v.end());
for (auto i:v)
gf(i)->x+=i->x;
}
void DFS()
{
LN t = root;
for (int i=0; i<s.length(); i++)
{
t = gp(t,s[i]);
t->x++;
}
}
int main()
{
ifstream cin("ahocorasick.in");
ofstream cout("ahocorasick.out");
ios_base::sync_with_stdio(false);
cin.tie(0);
string t;
cin>>t;
root = new Node();
root->fail = root;
cin>>n;
po = new LN[n];
for (int i=0; i<n; i++)
{
cin>>s;
id=i;
addkey(root,0);
}
s=t;
DFS();
Last();
for (int i=0; i<n; i++)
cout<<po[i]->x<<'\n';
return 0;
}