fail树就是将Trie图的Fail指针反指,从而生成一棵树,这个树的性质是:子节点对应字符串为以当前串为后缀,而子节点为原串的前缀,前缀的后缀就是嵌套在原串中的子串。

模板:BZOJ3172

Description

某人读论文,一篇论文是由许多单词组成。但他发现一个单词会在论文中出现很多次,现在想知道每个单词分别在论文中出现多少次。

Input

第一个一个整数N,表示有多少个单词,接下来N行每行一个单词。每个单词由小写字母组成,N<=200,单词长度不超过10^6

Output

输出N个整数,第i行的数字表示第i个单词在文章中出现了多少次。

Sample Input

3
a
aa
aaa

Sample Output

6
3
1
建完fail树统计子节点个数即可。
代码:
 #include<queue>
#include<cstdio>
#include<cstring>
#include<algorithm>
struct trnt{
int ch[];
int fl;
int wgt;
int hd;
}tr[];
struct ent{
int twd;
int lst;
}e[];
int fnd[];
char tmp[];
int cnt;
int siz;
int n;
std::queue<int>Q;
void ade(int f,int t)
{
cnt++;
e[cnt].twd=t;
e[cnt].lst=tr[f].hd;
tr[f].hd=cnt;
}
void add(char *a,int x)
{
int root=;
int len=strlen(a+);
for(int i=;i<=len;i++)
{
int c=a[i]-'a';
if(!tr[root].ch[c])
tr[root].ch[c]=++siz;
root=tr[root].ch[c];
tr[root].wgt++;
}
fnd[x]=root;
return ;
}
void Build()
{
int root=;
for(int i=;i<;i++)
if(tr[root].ch[i])
Q.push(tr[root].ch[i]);
while(!Q.empty())
{
root=Q.front();
Q.pop();
for(int i=;i<;i++)
{
if(tr[root].ch[i])
{
tr[tr[root].ch[i]].fl=tr[tr[root].fl].ch[i];
Q.push(tr[root].ch[i]);
}else
tr[root].ch[i]=tr[tr[root].fl].ch[i];
}
}
/*--------------------------以上是Trie图-------------------*/ /*--------------------------以下为fail树-------------------*/
for(int i=;i<=siz;i++)
ade(tr[i].fl,i);
return ;
}
void dfs(int x)
{
for(int i=tr[x].hd;i;i=e[i].lst)
{
int to=e[i].twd;
dfs(to);
tr[x].wgt+=tr[to].wgt;
}
}
int main()
{
scanf("%d",&n);
for(int i=;i<=n;i++)
{
scanf("%s",tmp+);
add(tmp,i);
}
Build();
dfs();
for(int i=;i<=n;i++)
printf("%d\n",tr[fnd[i]].wgt);
return ;
}

最新文章

  1. C++ Sqlite3
  2. WPF中Popup的几个问题
  3. Operation与GCD的不同
  4. 李洪强漫谈iOS开发[C语言-040]-switch case
  5. ubuntu 12.04下安装和配置kohana 3.3.3 的方法
  6. iOS 辛格尔顿
  7. php连接mysql数据库(新浪云SAE)
  8. VHDL学习记录
  9. C#中的反射 Reflection
  10. Debian 8.x / Ubuntu 16.04.x 搭建 Ghost 教程
  11. 命令 上传项目到git中
  12. Vue-父子组件传值
  13. Win2008r2 由ESXi 转换到 HyperV的处理过程
  14. html 绘制矩形轨迹,选中区域
  15. 试讲DOCKER专用
  16. MySQL数据库命令大全
  17. java中break,continue,标签实现goto效果(编程思想)
  18. 多尺度几何分析(Ridgelet、Curvelet、Contourlet、Bandelet、Wedgelet、Beamlet)
  19. 通过response向服务器用Io流写入图片
  20. ubuntu系统下的docker

热门文章

  1. OpenCv 人脸检測的学习
  2. Deferred Rendering(三)反锯齿和半透明问题
  3. 基于matlab的音频波形实时採集显示 v0.1
  4. Windows 7: Update is not applicable to your computer
  5. 逆波兰表达式解数学运算(c#)
  6. doT.js灵活运用之嵌入使用
  7. 剑指offer—java版本实现
  8. Linux下清除系统日志方法
  9. pigofzhou的巧克力棒
  10. 关于servlet的web.xml映射