洛谷P3966 单词 [TJOI2013] AC自动机
正解:AC自动机
解题报告:
先来提供一个40pts错解QAQ
首先看到这题就会想到AC自动机板子题2鸭!然后就照着那题的套路打一下,随便改一点儿,简单来说就是每次经过一个节点都要++,然后每搜到一个节点就暴跳所有fail,tr[fail].as+=tr[nw].as
然后你就能得到40pts的好成绩,,,另外60pts还是WA的,,,就很难过,,,
#include<bits/stdc++.h>
using namespace std;
#define ll int
#define rp(i,x,y) for(register ll i=x;i<=y;++i) const ll N=+,M=+;
ll n,cnt,as,ed[M];
struct tre{ll as,nxt[],fail;tre(){as=;memset(nxt,,sizeof(nxt));fail=;}}tr[N];
bool gdgs=; inline ll read()
{
register char ch=getchar();register ll x=;register bool y=;
while(ch!='-' && (ch>'' || ch<''))ch=getchar();
if(ch=='-')ch=getchar(),y=;
while(ch>='' && ch<='')x=(x<<)+(x<<)+(ch^''),ch=getchar();
return y?x:-x;
}
inline void bd(ll nm)
{
string str;cin>>str;ll lth=str.length()-,nw=;
rp(i,,lth)
{
if(tr[nw].nxt[str[i]-'a'+]==)tr[nw].nxt[str[i]-'a'+]=++cnt;
nw=tr[nw].nxt[str[i]-'a'+];++tr[nw].as;
}
ed[nm]=nw;
}
inline void fl()
{
queue<ll>Q;
rp(i,,)if(tr[].nxt[i])Q.push(tr[].nxt[i]);
while(!Q.empty())
{
ll nw=Q.front();Q.pop();
rp(i,,)
{
if(tr[nw].nxt[i])tr[tr[nw].nxt[i]].fail=tr[tr[nw].fail].nxt[i],Q.push(tr[nw].nxt[i]);
else tr[nw].nxt[i]=tr[tr[nw].fail].nxt[i];
}
}
}
inline void zdj()
{
rp(i,,cnt)
{
// printf("i=%d as=%d\n",i,tr[i].as);
for(register ll j=i;j;j=tr[j].fail)tr[tr[j].fail].as+=tr[i].as/*,printf("j=%d fl=%d\n",j,tr[j].fail)*/;
}
} int main()
{
n=read();rp(i,,n)bd(i);fl();tr[].fail=;zdj();//printf("QAQ?\n");
rp(i,,n)printf("%d\n",tr[ed[i]].as);
return ;
}
放下sd灵巧的sd代码呜呜呜
研究辣半天回来repo一下我错哪儿辣,,,我好像是打挂辣呜呜呜
不过还是有个点有问题
就是,暴跳会T
可以在配fail的时候记录下bfs序,然后直接按bfs倒叙序每次就只有这个点的fail要跳辣而不是所有的fail都要跳一遍
然后就over辣!
话说为什么这题居然有紫,,,?病毒都比这题难一些啊我jio得,,,?
等下放代码QAQ
#include<bits/stdc++.h>
using namespace std;
#define ll long long
#define rg register
#define rp(i,x,y) for(rg ll i=x;i<=y;++i)
#define my(i,x,y) for(rg ll i=x;i>=y;--i) const ll N=+,M=+;
ll n,cnt,as,ed[M],que[N],tmp;
struct tre{ll as,nxt[],fail;tre(){as=;memset(nxt,,sizeof(nxt));fail=;}}tr[N]; inline ll read()
{
rg char ch=getchar();rg ll x=;rg bool y=;
while(ch!='-' && (ch>'' || ch<''))ch=getchar();
if(ch=='-')ch=getchar(),y=;
while(ch>='' && ch<='')x=(x<<)+(x<<)+(ch^''),ch=getchar();
return y?x:-x;
}
inline void bd(ll nm)
{
string str;cin>>str;ll lth=str.length()-,nw=;
rp(i,,lth)
{
if(!tr[nw].nxt[str[i]-'a'+])tr[nw].nxt[str[i]-'a'+]=++cnt;
nw=tr[nw].nxt[str[i]-'a'+];++tr[nw].as;
}
ed[nm]=nw;
}
inline void fl()
{
queue<ll>Q;
rp(i,,)if(tr[].nxt[i])Q.push(tr[].nxt[i]),que[++tmp]=tr[].nxt[i];
while(!Q.empty())
{
ll nw=Q.front();Q.pop();
rp(i,,)
{
if(tr[nw].nxt[i])tr[tr[nw].nxt[i]].fail=tr[tr[nw].fail].nxt[i],Q.push(tr[nw].nxt[i]),que[++tmp]=tr[nw].nxt[i];
else tr[nw].nxt[i]=tr[tr[nw].fail].nxt[i];
}
}
} int main()
{
// freopen("cjkcjk.in","r",stdin);
// freopen("cjkcjk.out","w",stdout);
n=read();rp(i,,n)bd(i);fl();tr[].fail=;my(i,tmp,)tr[tr[que[i]].fail].as+=tr[que[i]].as;
rp(i,,n)printf("%lld\n",tr[ed[i]].as);
return ;
}
这儿是代码吼!
洛谷P3966 单词 [TJOI2013] AC自动机的更多相关文章
- 洛谷 - P3966 - 单词 - AC自动机
https://www.luogu.org/problemnew/show/P3966 因为文本串就是字典本身,所以这个和平时的AC自动机不太一样.平时的query要沿着fail树把子树的出现次数依次 ...
- 洛谷-P5357-【模板】AC自动机(二次加强版)
题目传送门 -------------------------------------- 过年在家无聊补一下这周做的几道AC自动机的模板题 sol:AC自动机,还是要解决跳fail边产生的重复访问,但 ...
- 洛谷P2444 病毒【AC自动机】
题目描述 二进制病毒审查委员会最近发现了如下的规律:某些确定的二进制串是病毒的代码.如果某段代码中不存在任何一段病毒代码,那么我们就称这段代码是安全的.现在委员会已经找出了所有的病毒代码段,试问,是否 ...
- 洛谷P2444 病毒 [POI2000] AC自动机
正解:AC自动机 解题报告: 传送门! 首先看到这种题目二话不说先把trie树和fail指针建立起来 然后就想鸭,如果我们想让模式串和文本串尽量不能匹配,就要想办法让它跳fail指针,而不是继续往下走 ...
- 洛谷2414(构建ac自动机fail树dfs序后遍历Trie树维护bit及询问答案)
要点 这是一道蔡队题,看我标题行事 任意询问y串上有多少个x串,暴力找每个节点是不是结尾肯定是炸的,考虑本质:如果某节点是x的结尾,根据ac自动机的性质,x一定是此(子)串后缀.又有每个Trie节点的 ...
- 洛谷-P3796-【模板】AC自动机(加强版)
题目传送门 -------------------------------------- 过年在家无聊补一下这周做的几道AC自动机的模板题 sol:AC自动机,在fail边的基础上再加一个last边, ...
- 【洛谷 P3966】 [TJOI2013]单词(AC自动机,差分)
把单词连起来,中间插入间隔符,同 #include <cstdio> #include <queue> #include <cstring> using names ...
- 洛谷.3808/3796.[模板]AC自动机
题目链接:简单版,增强版 简单版: #include <cstdio> #include <cstring> const int N=1e6+5,S=26; char s[N] ...
- 【BZOJ3172】[TJOI2013] 单词(AC自动机的小应用)
点此看题面 大致题意: 给你\(N\)个单词,请你求出每一个单词在这\(N\)个单词中出现的次数. 相关题目 这道题应该是洛谷上一道板子题的升级版. \(AC\)自动机 这是一道\(AC\)自动机的简 ...
随机推荐
- [OSX] 使用 MacPorts 安装 Python 和 pip 指南
Mac OS 未预装任何在 Unix/Linux 中常见的命令行包管理工具,Mac OS 中的 App Store 和自身的软件升级功能可以下载更新许多比较好的应用,但这些应用多数是满足普通消费者需求 ...
- iOS 事件的产生、传递、响应
一.事件的产生和传递 1.1.事件的产生 发生触摸事件后,系统会将该事件加入到一个由UIApplication管理的事件队列中为什么是队列而不是栈?因为队列的特定是先进先出,先产生的事件先处理才符合常 ...
- 转:Android开发:使用DDMS Heap进行内存泄露调试
无论怎么小心,想完全避免bad code是不可能的,此时就需要一些工具来帮助我们检查代码中是否存在会造成内存泄漏的地方.Android tools中的DDMS就带有一个很不错的内存监测工具Heap,本 ...
- 怎样用Windows10全屏流畅运行红色警戒2
https://jingyan.baidu.com/article/9113f81b1cb7f22b3214c724.html jpg 转 rar
- 【变态问题】在发现“XXXX”类型前实体框架已使用默认 DbConfiguration 实例。
今天在调试MVC反射调用EF写的dll 一直报错如下: 在发现“VipHallDbConfiguration”类型前实体框架已使用默认 DbConfiguration 实例.“VipHallDbCon ...
- linux mutex
#include <iostream> #include <queue> #include <cstdlib> #include <unistd.h> ...
- USACO The Clocks
操作间没有次序关系,同一个操作最多重复3次... 可以直接暴力... The Clocks IOI'94 - Day 2 Consider nine clocks arranged in a 3x3 ...
- 【WEB前端系列之CSS】CSS3动画之Tranition
前言 css中的transition允许css的属性值在一定的时间区间内平滑的过渡.这种效果可以在鼠标点击.获得焦点.被点击或对元素任何改变中触发,并圆滑的以动画效果改变CSS的属性值.语法: tra ...
- 【Eclipse】Ubuntu 下菜单栏失效了,怎么办?(已解决)
如果你的 Ubuntu 的版本是 13.10 , 且你又安装了 Eclipse , 你就会发现 Eclipse 的菜单不起作用了. 就是点击 File , Edit ... 这些菜单,不会显示子菜单了 ...
- Linux 下安装JDK1.8
本文主要介绍的是如何是Linux环境下安装JDK的,因为Linux环境下,很多时候也离不开Java的,下面笔者就和大家一起分享如何jdk1.8的过程吧. 一.安装环境 操作系统:Red Hat Ent ...