P3966 [TJOI2013]单词

题目链接:https://www.luogu.org/problemnew/show/P3966

题目描述

小张最近在忙毕设,所以一直在读论文。一篇论文是由许多单词组成但小张发现一个单词会在论文中出现很多次,他想知道每个单词分别在论文中出现了多少次。

输入输出格式

输入格式:

第一行一个整数N,表示有N个单词。接下来N行每行一个单词,每个单词都由小写字母(a-z)组成。(N≤200)

输出格式:

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

输入输出样例

输入样例#1: 复制

3
a
aa
aaa
输出样例#1: 复制

6
3
1

说明

数据范围

30%的数据, 单词总长度不超过10^3

100%的数据,单词总长度不超过10^6

题解:

这个题其实问的是一个单词在其它单词中出现的次数,题意有点不清晰吧= =

一个单词若在其它单词中出现,那么其它单词的那一条链上,至少会有一个fail指针指向这个单词的末尾,表面这个单词为目前结点的后缀。

那么我们可以考虑将fail指针翻转,构成一个fail树,那么若统计A单词在其它单词中的出现次数,就直接看以A为根的子树一共有多少个结点就行了。

总体思路就是这样,由于单词可能会重合,并且某些单词可能为另一些单词的前缀,那么我们首先可以记录一共有多少个单词经过单词A的尾节点,假设记为v,那么说明现在他作为前缀的情况有v个了。

之后便根据后面的结点的fail指针从下往上进行更新,来统计作为后缀的情况(注意这里必须从下往上才能保证正确性,并且时间复杂度也比较低),具体的方法就是根据bfs序来进行更新,因为bfs序越大的,那么说明它的深度肯定在更下面,反正不会在上面= =

代码如下:

#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N = 1e6+;
int n,tot;
char s[N];
int num[N],Q[N];
queue <int> q;
struct Aho_Corasick{
int Size;
int ch[N][];
int val[N];
int fail[N];
void init(){
Size=-;
newnode();
}
int newnode(){
memset(ch[++Size],,sizeof(ch[]));
fail[Size]=;
return Size;
}
void insert(char *s,int id){
int l=strlen(s);
int u=;
for(int i=;i<l;i++){
int idx=s[i]-'a';
if(!ch[u][idx]) ch[u][idx]=newnode();
u=ch[u][idx];
num[u]++;
}
val[id]=u;
}
void Getfail(){
while(!q.empty()) q.pop();
for(int i=;i<;i++){
if(ch[][i]) q.push(ch[][i]);
}
while(!q.empty()){
int cur=q.front();q.pop();
Q[++tot]=cur;
for(int i=;i<;i++){
if(ch[cur][i]){
fail[ch[cur][i]]=ch[fail[cur]][i];
q.push(ch[cur][i]);
}else{
ch[cur][i]=ch[fail[cur]][i];
}
}
}
}
}ac;
int main(){
cin>>n;
ac.init();
for(int i=;i<=n;i++){
scanf("%s",s);
ac.insert(s,i);
}
ac.Getfail();
for(int i=tot;i>=;i--) num[ac.fail[Q[i]]]+=num[Q[i]];
for(int i=;i<=n;i++){
printf("%d\n",num[ac.val[i]]);
}
return ;
}

洛谷P3966 [TJOI2013]单词(fail树性质)的更多相关文章

  1. 洛谷P3966 [TJOI2013]单词(AC自动机)

    题目描述 小张最近在忙毕设,所以一直在读论文.一篇论文是由许多单词组成但小张发现一个单词会在论文中出现很多次,他想知道每个单词分别在论文中出现了多少次. 输入输出格式 输入格式: 第一行一个整数N,表 ...

  2. [洛谷P3966][TJOI2013]单词

    题目大意:有$n$个字符串,求每个字符串在所有字符串中出现的次数 题解:$AC$自动机,每个节点被经过时$sz$加一,每一个字符串出现次数为其$fail$树子树$sz$和 卡点:$AC$自动机根节点为 ...

  3. 洛谷P3966 [TJOI2013]单词(后缀自动机)

    传送门 统计单词出现次数……为啥大家都是写AC自动机的嘞……明明后缀自动机也能做的说…… 统计出现次数这个就直接按长度排序然后做个dp就好,这是SAM的板子的要求啊,不提了 然后考虑怎么让所有串之间隔 ...

  4. BZOJ3172 & 洛谷3966 [Tjoi2013]单词 【fail树】

    3172: [Tjoi2013]单词 Time Limit: 10 Sec  Memory Limit: 512 MB Submit: 4293  Solved: 2083 [Submit][Stat ...

  5. 洛谷P2412 查单词 [trie树 RMQ]

    题目背景 滚粗了的HansBug在收拾旧英语书,然而他发现了什么奇妙的东西. 题目描述 udp2.T3如果遇到相同的字符串,输出后面的 蒟蒻HansBug在一本英语书里面找到了一个单词表,包含N个单词 ...

  6. bzoj 3172: [Tjoi2013]单词 fail树

    题目大意: 一篇论文是由许多单词组成,现在想知道每个单词分别在论文中出现多少次. 题解: 我们首先考虑fail指针的含义 如果fail[x] = y,那么我们就知道y作为x的后缀在x中出现了一次 所以 ...

  7. P3966 [TJOI2013]单词

    P3966 [TJOI2013]单词 题目描述 小张最近在忙毕设,所以一直在读论文.一篇论文是由许多单词组成但小张发现一个单词会在论文中出现很多次,他想知道每个单词分别在论文中出现了多少次. 输入输出 ...

  8. 洛谷 P3384 【模板】树链剖分-树链剖分(点权)(路径节点更新、路径求和、子树节点更新、子树求和)模板-备注结合一下以前写的题目,懒得写很详细的注释

    P3384 [模板]树链剖分 题目描述 如题,已知一棵包含N个结点的树(连通且无环),每个节点上包含一个数值,需要支持以下操作: 操作1: 格式: 1 x y z 表示将树从x到y结点最短路径上所有节 ...

  9. 洛谷p3384【模板】树链剖分题解

    洛谷p3384 [模板]树链剖分错误记录 首先感谢\(lfd\)在课上调了出来\(Orz\) \(1\).以后少写全局变量 \(2\).线段树递归的时候最好把左右区间一起传 \(3\).写\(dfs\ ...

随机推荐

  1. yii的学习笔记 基本结构 自用

    Yii 学习笔记 W:YII是什么? Q:Yii 是一个基于组件的高性能 PHP 框架,用于快速开发大型 Web 应用.它使Web开发中的 可复用度最大化,可以显著提高你的Web应用开发速度.Yii ...

  2. leetcode-最长上升子序列LIS

    转载原文地址:http://www.cnblogs.com/GodA/p/5180560.html 给定一个无序的整数数组,找到其中最长上升子序列的长度. 示例: 输入: [10,9,2,5,3,7, ...

  3. 爬虫2.1-scrapy框架-两种爬虫对比

    目录 scrapy框架-两种爬虫对比和大概流程 1. 传统spider爬虫 2. crawl型爬虫 3. 循环页面请求 4. scrapy框架爬虫的大致流程 scrapy框架-两种爬虫对比和大概流程 ...

  4. 给eclipse安装color-theme插件

    给eclipse安装color-theme插件 2016年03月22日 19:16:01 ming_love 阅读数:5193 标签: Eclipse Color Theme 更多 个人分类: jav ...

  5. jQuery 对象 与 原生 DOM 对象 相互转换

    区别 jQuery 选择器得到的 jQuery对象 和 原生JS 中的document.getElementById() document.querySelector取得的 DOM对象 是两种不同类型 ...

  6. Juice账号

    zhangxiaocong69 zxc6545398 15657167502 区块链账户: 0x00680404766965143796a0a070835c3cdf9a4a50

  7. php面试的那些“黑话”

    以下是一些常见的面试暗语,求职者一定要弄清楚其中蕴含的深意,不然可能“躺着也中枪”,最后只能铩羽而归. (1)请把简历先放在这,有消息我们会通知你的 面试官说出这句话,则表明他对你已经“兴趣不大”,为 ...

  8. HDU 3265/POJ 3832 Posters(扫描线+线段树)(2009 Asia Ningbo Regional)

    Description Ted has a new house with a huge window. In this big summer, Ted decides to decorate the ...

  9. finecms

    finecms地址 还不错的国内CMS http://www.dayrui.com/doc/246.html

  10. python学习笔记01:安装python

    下载python: 从从https://www.python.org/downloads/下载python,根据操作系统的不同,选择不同的版本下载.注意:linux系统大多预装了python,可以直接 ...