BZOJ2555: SubString(后缀自动机,LCT维护Parent树)
Description
Input
Output
Sample Input
A
QUERY B
ADD BBABBBBAAB
Sample Output
解题思路:
代码:
#include<cstdio>
#include<cstring>
#include<algorithm>
#define lll tr[spc].ch[0]
#define rrr tr[spc].ch[1]
#define ls ch[0]
#define rs ch[1]
class Unzip{
public:
void update(int lastans)
{
mask^=lastans;
return ;
}
void decode(int *a,int len)
{
int upg=mask;
for(int i=;i<=len;i++)
tmp[i-]=a[i];
for(int i=;i<len;i++)
{
upg=(upg*+i)%len;
std::swap(tmp[i],tmp[upg]);
}
for(int i=;i<=len;i++)
a[i]=tmp[i-];
return ;
}
private:
int tmp[];
int mask;
}U;
struct trnt{
int ch[];
int fa;
int is;
int lzt;
int wgt;
int wgti;
bool anc;
}tr[];
struct sant{
int tranc[];
int len;
int pre;
}s[];
int Q;
int siz;
int fin;
int lasans;
char tmp[];
int atp[];
bool whc(int spc)
{
return tr[tr[spc].fa].rs==spc;
}
void pushup(int spc)
{
tr[spc].wgt=tr[spc].wgti+tr[spc].is+tr[lll].wgt+tr[rrr].wgt;
return ;
}
void trr(int spc)
{
if(!spc)
return ;
std::swap(lll,rrr);
tr[spc].lzt^=;
return ;
}
void pushdown(int spc)
{
if(tr[spc].lzt)
{
trr(lll);
trr(rrr);
tr[spc].lzt=;
}
return ;
}
void recal(int spc)
{
if(!tr[spc].anc)
recal(tr[spc].fa);
pushdown(spc);
return ;
}
void rotate(int spc)
{
int f=tr[spc].fa;
bool k=whc(spc);
tr[f].ch[k]=tr[spc].ch[!k];
tr[spc].ch[!k]=f;
if(tr[f].anc)
{
tr[f].anc=;
tr[spc].anc=;
}else
tr[tr[f].fa].ch[whc(f)]=spc;
tr[spc].fa=tr[f].fa;
tr[f].fa=spc;
tr[tr[f].ch[k]].fa=f;
pushup(f);
pushup(spc);
return ;
}
void splay(int spc)
{
recal(spc);
while(!tr[spc].anc)
{
int f=tr[spc].fa;
if(tr[f].anc)
{
rotate(spc);
return ;
}
if(whc(spc)^whc(f))
rotate(spc);
else
rotate(f);
rotate(spc);
}
return ;
}
void access(int spc)
{
int lst=;
while(spc)
{
splay(spc);
tr[spc].wgti-=tr[lst].wgt;
tr[spc].wgti+=tr[rrr].wgt;
tr[rrr].anc=;
tr[lst].anc=;
rrr=lst;
pushup(spc);
lst=spc;
spc=tr[spc].fa;
}
return ;
}
void Mtr(int spc)
{
access(spc);
splay(spc);
trr(spc);
return ;
}
void split(int x,int y)
{
Mtr(x);
access(y);
splay(y);
return ;
}
void link(int x,int y)
{
split(x,y);
tr[x].fa=y;
tr[y].wgti+=tr[x].wgt;
pushup(y);
return ;
}
void cut(int x,int y)
{
split(x,y);
tr[x].fa=;
tr[y].ls=;
tr[x].anc=;
pushup(y);
return ;
}
void Insert(int c)
{
int nwp,nwq,lsp,lsq;
nwp=++siz;
tr[nwp].anc=;
tr[nwp].is=;
s[nwp].len=s[fin].len+;
for(lsp=fin;lsp&&!s[lsp].tranc[c];lsp=s[lsp].pre)
s[lsp].tranc[c]=nwp;
if(!lsp)
{
s[nwp].pre=;
link(nwp,);
}else{
lsq=s[lsp].tranc[c];
if(s[lsq].len==s[lsp].len+)
{
s[nwp].pre=lsq;
link(nwp,lsq);
}else{
nwq=++siz;
tr[nwq].anc=;
s[nwq]=s[lsq];
cut(s[lsq].pre,lsq);
link(s[nwq].pre,nwq);
s[nwq].len=s[lsp].len+;
s[nwp].pre=s[lsq].pre=nwq;
link(nwq,nwp);
link(nwq,lsq);
while(s[lsp].tranc[c]==lsq)
{
s[lsp].tranc[c]=nwq;
lsp=s[lsp].pre;
}
}
}
fin=nwp;
return ;
}
int Query(int root)
{
Mtr();
access(root);
return tr[root].wgti+tr[root].is;
}
int main()
{
fin=++siz;
tr[fin].anc=;
scanf("%d",&Q);
scanf("%s",tmp+);
int len=strlen(tmp+);
for(int i=;i<=len;i++)
Insert(tmp[i]-'A');
while(Q--)
{
scanf("%s",tmp);
if(tmp[]=='A')
{
scanf("%s",tmp+);
len=strlen(tmp+);
for(int i=;i<=len;i++)
atp[i]=tmp[i]-'A';
U.decode(atp,len);
for(int i=;i<=len;i++)
Insert(atp[i]);
}else{
scanf("%s",tmp+);
len=strlen(tmp+);
for(int i=;i<=len;i++)
atp[i]=tmp[i]-'A';
U.decode(atp,len);
int root=;
for(int i=;i<=len;i++)
{
root=s[root].tranc[atp[i]]; }
if(!root)
lasans=;
else
lasans=Query(root);
printf("%d\n",lasans);
U.update(lasans);
}
}
return ;
}
BZOJ2555: SubString(后缀自动机,LCT维护Parent树)的更多相关文章
- bzoj 2555 SubString —— 后缀自动机+LCT
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=2555 建立后缀自动机,就可以直接加入新串了: 出现次数就是 Right 集合的大小,需要查询 ...
- luogu5212/bzoj2555 substring(后缀自动机+动态树)
对字符串构建一个后缀自动机. 每次查询的就是在转移边上得到节点的parent树中后缀节点数量. 由于强制在线,可以用动态树维护后缀自动机parent树的子树和. 注意一个玄学的优化:每次在执行连边操作 ...
- 【BZOJ2555】SubString 后缀自动机+LCT
[BZOJ2555]SubString Description 懒得写背景了,给你一个字符串init,要求你支持两个操作 (1):在当前字符串的后面插入一个字符串 (2 ...
- [Bzoj3676][Apio2014]回文串(后缀自动机)(parent树)(倍增)
3676: [Apio2014]回文串 Time Limit: 20 Sec Memory Limit: 128 MBSubmit: 3396 Solved: 1568[Submit][Statu ...
- bzoj 3881 [Coci2015]Divljak——LCT维护parent树链并
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=3881 对 S 建 SAM ,每个 T 会让 S 的 parent 树的链并答案+1:在 T ...
- bzoj 2555: SubString 后缀自动机+LCT
2555: SubString Time Limit: 30 Sec Memory Limit: 512 MBSubmit: 688 Solved: 235[Submit][Status][Dis ...
- bzoj 2555 SubString——后缀自动机+LCT
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=2555 要维护 right 集合的大小.因为 fa 会变,且 fa 构成一棵树,所以考虑用 L ...
- BZOJ2555 SubString 【后缀自动机 + LCT】
题目 懒得写背景了,给你一个字符串init,要求你支持两个操作 (1):在当前字符串的后面插入一个字符串 (2):询问字符串s在当前字符串中出现了几次?(作为连续子串) 你必须在线支持这些操作. 输入 ...
- BZOJ2555 SubString(后缀自动机+LCT)
询问串放在SAM上不跳fail跑到的节点的|right|即为答案.用LCT维护parent树即可.可以直接维护子树信息,也可以转化为路径加.注意强制在线所使用的mask是作为参数传进去的. #incl ...
随机推荐
- Haproxy压测
目的:测试Haproxy压测情况 环境: Ha服务器:8核16G虚机,后端6个2核4G,压测客户端3个2核4G 安装和优化: 一.Haproxy #cd /opt/soft #wget http:// ...
- BZOJ 3224 平衡树模板题
Treap: //By SiriusRen #include <cstdio> #include <algorithm> using namespace std; int n, ...
- ivms4200 远程桌面访问测试过程及问题汇总
17.11.4 测试存储服务器配置后能否自动录像确认 10:34 4200客户端关闭 10:40 打开4200客户端软件 10:51 关机 10:56 开机,有提示出现,“防火墙阻止... ...
- WPF中Image控件的Source属性
原文:WPF中Image控件的Source属性 imgBook 是一个Image控件,在后台代码中我想给它指定Source的属性.我先如下方式进行: Uri uri = new Uri(strImag ...
- XML解析——SAX解析以及更方便的解析工具(JDOM、DOM4J)
XML主要用于数据交换,HTML则用于显示. 相对于DOM的树形解析,SAX采用的是顺序解析,这种解析方法可以快速地读取XML数据的方式. SAX主要事件: No. 方法 类型 描述 1 public ...
- 【iOS开发-88】事件传递原理解释哪个控件处理事件以及响应者链条的介绍
一.触摸事件传递原理 (1)大的方向是:从父控件传递给子控件. --父控件会先检查自己能否接受事件的处理 --然后再看看触摸在不在自己的范围内 --假设在的话,就遍历子控件.看看有没有合适的子控件能够 ...
- Android实现本地图片选择及预览缩放效果仿春雨医生
在做项目时常常会遇到选择本地图片的需求.曾经都是懒得写直接调用系统方法来选择图片.可是这样并不能实现多选效果.近期又遇到了,所以还是写一个demo好了.以后也方便使用.还是首先来看看效果 显示的图片使 ...
- Oracle-02-数据库概述
一.数据库用途 用于存放数据的软件 当中Application server重要,将数据存在表中每一个表关系就能够反映不同表之间数据的关系,比方淘宝用户注冊.商品买卖等数据存在操作系统的目录中,不便于 ...
- 一个Java基础练习
今天在群里又有一个朋友问到了这样一个练习,我索性将代码贴到这里,下次须要的朋友能够来这里看. 用到知识点:数组.集合.IO流 问题描写叙述:在例如以下图所看到的的一个txt文件里读取数据到内存,然后统 ...
- Javascript函数的基本概念+匿名立即执行函数
函数声明.函数表达式.匿名函数 函数声明:function fnName () {…};使用function关键字声明一个函数,再指定一个函数名,叫函数声明. 函数表达式 var fnName = f ...