【bzoj2555】Substring【后缀平衡树入门】

传送门

(bzoj上不去我也很无奈啊)

题意:维护一个字符串,支持后面加字符串,给定串询问出现次数。强制在线。

数据范围:暴力跑不过

前置知识:重量平衡树

众所周知,平衡树都用了一些策略保证平衡。

平衡有三种:严格平衡,均摊平衡,期望平衡

其中严格平衡和期望平衡的(当然不是很严格,规模上是平衡的就可以了)称为重量平衡树。(该定义存疑)

这种平衡树每次操作对树的结构影响很小(最大的子树为log级别)。这意味着你可以用它维护子树规模的集合。

也就是说可以在里面套一个动态开点线段树维护子树的所有权值。

常见的有替罪羊树和treap。

(fhq好像也可以,但好像没人用……)

以维护子树集合为例,替罪羊树每次重构的时候暴力更新集合。

treap就比较玄学,旋转完后暴力更新,期望是log的……


回到这道题,我们需要一个叫后缀平衡树的黑科技。

其实就是用重量平衡树维护后缀数组。

首先把所有串倒序,注意是假装一来就是倒的,显然不影响答案,只是改成了在前面加。

把字符一个一个添加,这样每添加一个只会多一个后缀,只需要把这个后缀插入平衡树。

注意:把添加的字符按顺序记下来,这样得到的串是输入顺序,但实际上是倒着存的。

现在的问题是如何快速比较两个后缀。

由于新来的后缀不在树上,但之前的树上的后缀是可以快速比较的。

所以我们比较第一个字符,如果一样就丢掉然后在树上比较。

显然可以O(logn)O(logn)O(logn)做。一个技巧,对于每个节点维护(l,r)(l,r)(l,r),其权值为val=l+r2val=\frac{l+r}2val=2l+r,左儿子(l,val)(l,val)(l,val),右儿子(val,r)(val,r)(val,r),可以直接用权值O(1)O(1)O(1)比较,因为深度是logloglog的,精度可以保证。 重构时暴力更新。

询问的时候查比SSS小的后缀数,再在后面加一个很大的字符再查一次,两个减一下。由于深度是logloglog的,所以直接暴力比较复杂度是O(∣S∣logn)O(|S|logn)O(Slogn)

莫名觉得比后缀数组好写是怎么回事

#include <iostream>
#include <cstdio>
#include <cstring>
#include <cctype>
#include <algorithm>
//#include <windows.h>
#include <cassert>
#define MAXN 3600005
using namespace std;
const double alpha=0.7;
char c[MAXN];
int ch[MAXN][2],siz[MAXN],rt,tot;
double L[MAXN],R[MAXN];
inline double val(const int& x){return x?L[x]+R[x]:-1e6;}
inline bool cmp(const int& x,const int& y){return c[x]<c[y]||(c[x]==c[y]&&val(x-1)<val(y-1));}
int p[MAXN];
void dfs(int u)
{if (ch[u][0]) dfs(ch[u][0]);p[++p[0]]=u;if (ch[u][1]) dfs(ch[u][1]);
}
void build(int& x,int l,int r,double vl,double vr)
{if (l>r) return (void)(x=0);int mid=(l+r)>>1;x=p[mid];siz[x]=r-l+1;L[x]=vl;R[x]=vr;double vmid=(vl+vr)/2;build(ch[x][0],l,mid-1,vl,vmid);build(ch[x][1],mid+1,r,vmid,vr);
}
void insert(int& x,int i,double l,double r)
{if (!x) return (void)(siz[x=i]=1,L[x]=l,R[x]=r);if (siz[ch[x][0]]>siz[x]*alpha||siz[ch[x][1]]>siz[x]*alpha){p[0]=0;dfs(x);build(x,1,p[0],l,r);}++siz[x];L[x]=l;R[x]=r;double mid=(l+r)/2;if (cmp(i,x)) insert(ch[x][0],i,l,mid);else insert(ch[x][1],i,mid,r);
}
inline void insert(char i){c[++tot]=i;insert(rt,tot,0,1e6);}
int de;
int query(int x,char *s,int len)
{if (!x) return 0;int i;for (i=0;s[i]==c[x-i]&&i<len;i++);if (i==len||s[i]<c[x-i]) return query(ch[x][0],s,len);else{de=x;int res=siz[ch[x][0]]+1+query(ch[x][1],s,len);return res;}
}
char s[MAXN];
int len,mask;
inline void read(int type)
{#ifndef ONLINE_JUDGE type=0;#endifscanf("%s",s);len=strlen(s);if (type){int t=mask;for (int i=0;i<len;i++) swap(s[i],s[t=(t*131+i)%len]);	}
}
int main()
{int q;scanf("%d",&q);read(0);for (int i=0;i<len;i++)	insert(s[i]);while (q--){read(0);if (s[0]=='A'){read(1);for (int i=0;i<len;i++) insert(s[i]);}else{read(1);reverse(s,s+len);int ans=-query(rt,s,len);int t=de;s[len]='Z'+1;ans+=query(rt,s,len+1);printf("%d\n",ans);mask^=ans;}}return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/315168.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

.NET Core 3.0之深入源码理解Kestrel的集成与应用(一)

写在前面ASP.NET Core 的 Web 服务器默认采用Kestrel&#xff0c;这是一个基于libuv(一个跨平台的基于Node.js的异步I/O库)的跨平台、轻量级的Web服务器。在开始之前&#xff0c;先回顾一下.NET Core 3.0默认的main()方法模板中&#xff0c;我们会调用Host.CreateDefaultBuilde…

HTTP状态码的类别

状态码类别类别原因短语1XX信息性状态码接受的请求正在处理2XX成功状态码请求正常处理完毕3XX重定向状态码需要进行附加操作以完成请求4XX客户端错误状态码服务器无法处理请求5XX服务器错误状态码 服务器处理请求出错 HTTP状态码的数量高达60余种&#xff0c;下面为大家介绍比…

P2596 [ZJOI2006]书架 无旋treap 按照排名分裂

传送门 文章目录题意&#xff1a;思路&#xff1a;题意&#xff1a; 实现如下操作&#xff1a; 思路&#xff1a; fhq-treap板子辣&#xff0c;不要被他的编号误导了&#xff0c;我们还是需要按照排名来分裂&#xff0c;从上到下标号1−n1-n1−n即可&#xff0c;注意在按照…

【水】几个网络流图论模型的记录

DAG相关 最小路径覆盖 定义&#xff1a;最少不重路径覆盖DAG 初始时每个点是独立的 之后每次加一条边把两个点连到一起 因为只能用一次&#xff0c;所以是个最大匹配 最小路径覆盖N-拆点后最大匹配\text{最小路径覆盖N-拆点后最大匹配}最小路径覆盖N-拆点后最大匹配 最小链…

surging 微服务引擎 2.0 会有多少惊喜?

surging 微服务引擎从2017年6月至今已经有两年的时间&#xff0c;这两年时间有多家公司使用surging 服务引擎&#xff0c;并且有公司搭建了CI/CD&#xff0c;并且使用了k8s 集群&#xff0c;这里我可以说下几家公司的服务搭建情况&#xff0c;公司名不便透露&#xff0c;我们就…

MySQL中存在索引但不能索引的经典场景(笔记)

以%开头的LIKE查询不能使用B-Tree索引 这个是因为B-Tree数的结构决定的&#xff0c;一般推荐使用全文索引来解决类似的全文检索的问题数据类型出现隐式转换的时候也不会使用索引不满足最左前缀原则的情况下也不会使用到索引如果全表扫描比索引快的话&#xff0c;则不使…

Codeforces Round #630 (Div. 2) E. Height All the Same 排列组合

传送门 文章目录题意&#xff1a;思路&#xff1a;题意&#xff1a; 思路&#xff1a; 由于n,mn,mn,m都很大&#xff0c;不难猜到这是一个公式题。 首先化简题目中的两个操作&#xff0c;第二个操作就是可以让奇偶性相同的位置的高度相同。第一个操作虽然是改变相邻两个的奇偶…

【洛谷P4719】动态DP【LCT】【矩阵】

之前的后缀平衡树其实没完&#xff0c;只是过于鬼畜就弃了 传送门 题意&#xff1a;带修改点权的最大独立集 N≤1e5N \leq 1e5N≤1e5 一个没啥用的模板&#xff0c;不过适合练习LCT 先写出方程 f(u,0)∑v∈son(u)max{f(v,0),f(v,1)}f(u,0)\sum_{v \in son(u)}max\{f(v,0),f…

对产品质量的一点思考

不管是做产品还是做项目&#xff0c;也不管是采用瀑布模型还是敏捷开发&#xff0c;我们都有一个终极目标&#xff0c;就是能按时交付质量可靠的功能&#xff0c;其中质量尤为重要。本文是我对产品质量的一点思考&#xff0c;如果您所在的团队代码质量很高&#xff0c;很少出BU…

操作系统-学习笔记

王道操作系统&#xff1a;有道云笔记 欢迎评论给意见&#xff01;

Codeforces Round #630 (Div. 2) F. Independent Set 树形dp

传送门 文章目录题意&#xff1a;思路&#xff1a;题意&#xff1a; 给你一棵树&#xff0c;求这棵树的边导出子图中独立集的数量和&#xff0c;独立集大小可以为000。 思路&#xff1a; 先考虑普通的独立集数量怎么求&#xff0c;无非就是分情况讨论一下选根还是不选根&…

CSP赛前总结

1.由奥卡姆剃刀定律&#xff0c;通过各种特判和大量无根据猜测得到的解法不可能正确。 比赛的题目解法可能复杂&#xff0c;但绝不会繁琐。 2.由幸存者偏差&#xff0c;在写题时往往会参考样例&#xff0c;这样样例以外的情况可能会导致bug。 不要相信样例&#xff0c;大样例…

正确使用AES对称加密

正确使用AES对称加密经常我看到项目中有人使用了对称加密算法&#xff0c;用来加密客户或项目传输中的部分数据。但我注意到开发 人员由于不熟悉原理&#xff0c;或者简单复制网上的代码示例&#xff0c;有导致代码存在安全风险。我经常遇到的问题&#xff0c;有如下&#xff1…

Codeforces Round #709 (Div. 1) C. Skyline Photo dp + 单调栈优化

传送门 文章目录题意&#xff1a;思路&#xff1a;题意&#xff1a; 思路&#xff1a; 首先一个非常明显的dpdpdp式子就是f[i]max(f[j]val(j1,i))f[i]max(f[j]val(j1,i))f[i]max(f[j]val(j1,i))&#xff0c;其中val(j1,i)val(j1,i)val(j1,i)是[j1,i][j1,i][j1,i]中高度最小的美…

CSP2019游记

Day -不知道多少 第一轮 题出得挺好&#xff0c;终于没有鬼畜的CCF赞歌了 考得还行 Day -1 复习了Tarjan并伪证了一遍&#xff0c;然后颓废了 安利E17大失败 放了几十个满贯 给某同学科普了一些不好的东西&#xff0c;现在他好像自闭了 我谢罪 Day 0 继续肝Tarjan然后…

「数据分析」Sqlserver中的窗口函数的精彩应用之数据差距与数据岛(含答案)...

上一篇介绍过数据差距与数据岛的背景&#xff0c;这里不再赘述&#xff0c;请翻阅上一文。此篇在Sqlserver上给大家演示1000万条记录的计算性能。测试电脑软硬件说明一般般的笔记本电脑&#xff0c;2017年7月&#xff0c;价格&#xff1a;4500。电脑配置数据构造1000万行数据&a…

Codeforces Round #631 (Div. 2) C. Dreamoon Likes Coloring 构造

传送门 文章目录题意&#xff1a;思路&#xff1a;题意&#xff1a; 思路&#xff1a; 针灸思维不行&#xff0c;数据结构来凑呗。 一开始做的时候想简单了&#xff0c;一直wawawa&#xff0c;后来想到了hackhackhack样例&#xff0c;开始换思路构造&#xff0c;结果死活想不到…

用象棋的思维趣说IT人的职业发展和钱途

最近我花了不少功夫在学习象棋&#xff0c;也学习了王天一等高手的棋路&#xff0c;感觉IT人的职业和下棋一样&#xff0c;往好了讲&#xff0c;争主动权争实惠只争朝夕&#xff0c;往坏了讲&#xff0c;一步走错得用多步来弥补&#xff0c;如果错误太大未必能弥补回来。在本文…

【康复训练】[国家集训队] calc【dp】【拉格朗日插值】

传送门 显然可以dp 显然可以假设单调增&#xff0c;答案乘个阶乘即可 设f(i,j)f(i,j)f(i,j)表示前iii个不超过jjj的答案 f(i,j)f(i,j−1)jf(i−1,j−1)f(i,j)f(i,j-1)jf(i-1,j-1)f(i,j)f(i,j−1)jf(i−1,j−1) 注意边界是f(0,i)1!f(0,i)1!f(0,i)1! 注意边界是f(0,i)1!!f(0…

Codeforces Round #631 (Div. 2) D. Dreamoon Likes Sequences 思维 + 组合数学

传送门 文章目录题意&#xff1a;思路&#xff1a;题意&#xff1a; 给你d,modd,modd,mod&#xff0c;让你求能构造出如下序列aaa的个数模modmodmod&#xff1a; 思路&#xff1a; 首先可以发现aaa的长度不能超过log2dlog_2dlog2​d&#xff0c;因为如果存在两个aaa的二进制…