#include <bits/stdc++.h>
using namespace std;
const int N=2e5+5;
int n,cnt=0,didx=0,idx[N],ans[N];
string s[N];
struct Node
{
int son[26],idx,fail,ans;
Node()
{
memset(son,0,sizeof(son));
idx=fail=ans=0;
}
};
vector<vector<int>> failt;
vector<Node> tr;
void jf()
{
queue<int> q;
for(int i=0;i<26;i++)
if(tr[0].son[i])
{
q.push(tr[0].son[i]);
failt[0].push_back(tr[0].son[i]);//用于建立fail的树,注意是反向建边
}
while(!q.empty())
{
int t=q.front();
q.pop();
for(int i=0;i<26;i++)
{
if(tr[t].son[i])
{
tr[tr[t].son[i]].fail=tr[tr[t].fail].son[i];
q.push(tr[t].son[i]);
failt[tr[tr[t].fail].son[i]].push_back(tr[t].son[i]);//用于建立fail的树,注意是反向建边
}
else
tr[t].son[i]=tr[tr[t].fail].son[i];
}
}
}
void query()
{
string st;
cin>>st;
int u=0;
for(char x:st)
{
u=tr[u].son[x-'a'];
tr[u].ans+=1;
}
}
void dfs(int u)
{
for(int v:failt[u])
{
dfs(v);
tr[u].ans+=tr[v].ans;//回溯时统计
}
ans[tr[u].idx]=tr[u].ans;
}
int main()
{
cin>>n;
tr.emplace_back();
for(int i=1;i<=n;i++)
{
string st;
cin>>st;
int u=0;
for(char x:st)
{
if(!tr[u].son[x-'a'])
{
tr[u].son[x-'a']=++cnt;
tr.emplace_back();
}
u=tr[u].son[x-'a'];
}
//上面是建树
if(!tr[u].idx)
tr[u].idx=++didx;
idx[i]=tr[u].idx;//idx数组去重用
}
failt.resize(tr.size());
jf();
query();
dfs(0);
for(int i=1;i<=n;i++)
cout<<ans[idx[i]]<<"\n";
}