bzoj1014火星人
...强迫症终于A了这道题 bzoj前30道全A指日可待
splay维护这个结点控制的字符串的hash值
每次旋转重新算一遍就可以了
查询的时候跑一个二分
讲起来很简单但是还是调了1h才调对了splay
把main写完饺子都凉了
没写过几次平衡树 常数写的奇大 能递归的我都递归了。。。
字符串哈希因为过于Naive只会用自然溢出。。。
但是1A了
家里的电脑有写好的read和write
我竟然忘了。。。
#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cmath>
#include<cstring>
#include<algorithm>
#include<vector>
#include<queue>
#include<set>
#include<map>
#include<stack>
#define ll unsigned long long
#define pi 3.14
#define eps 1e-9
#define inf 2147483233
#define m(a) memset(a,0,sizeof(a))
#define M(a) memset(a,127,sizeof(a))
#define REP(i,m,n) for(int i=1;i<=n;i++)
#define DWN(i,n,m) for(int i=n;i>=1;i++)
#define lowbit(x) x&(-x)
using namespace std;
int n;
inline int read()
{
int x=,f=;
char ch=getchar();
while(!isdigit(ch)){if(ch=='-')f=-;ch=getchar();}
while(isdigit(ch)){x=*x+ch-'';ch=getchar();}
return x*f;
}
inline void write(int x)
{
int num=;
char buf[];
while(x)buf[++num]=(x%)+'',x/=;
while(num)putchar(buf[num--]);
putchar('\n');
}
ll powe[];
void makepow()
{
int i;
for(powe[]=,i=;i<;i++)powe[i]=powe[i-]*;
}
const int maxn=;
char str[maxn];
struct SplayTree
{
int rt,Size;
int son[maxn][],f[maxn],size[maxn];
ll val[maxn],hsh[maxn];
char s[maxn];
inline void pushup(int x){size[x]=size[son[x][]]+size[son[x][]]+;hsh[x]=hsh[son[x][]]+powe[size[son[x][]]]*s[x]+powe[size[son[x][]]+]*hsh[son[x][]];}
inline void Rotate(int x,int type)
{
int y=f[x];
son[y][!type]=son[x][type];
f[son[x][type]]=y;
f[x]=f[y];
if(f[x])son[f[y]][son[f[y]][]==y]=x;
son[x][type]=y;
f[y]=x;
size[x]=size[y],hsh[x]=hsh[y];
pushup(y);
}
inline void splay(int x,int goal)
{
while(f[x]!=goal)
{
if(f[f[x]]==goal)
{
if(son[f[x]][]==x)Rotate(x,);
else Rotate(x,);
}
else
{
int y=f[x],z=f[y];
if(son[z][]==y)
{
if(son[y][]==x)Rotate(y,),Rotate(x,);
else Rotate(x,),Rotate(x,);
}
else
{
if(son[y][]==x)Rotate(y,),Rotate(x,);
else Rotate(x,),Rotate(x,);
}
}
}
if(goal==) rt=x;
}
inline int rank(int x,int k)
{
if(k<=size[son[x][]]) return rank(son[x][],k);
else if(k==size[son[x][]]+) return x;
else return rank(son[x][],k-size[son[x][]]-);
}
inline int build(int l,int r,int id)
{
if(l>r)return ;
int x=++Size,mid=(l+r)>>;
f[x]=id;
s[x]=str[mid];
son[x][]=build(l,mid-,x);
son[x][]=build(mid+,r,x);
pushup(x);
return x;
}
inline void insert(int k,char val)
{
int x=rank(rt,k),y=rank(rt,k+);
splay(x,),splay(y,x);
s[++Size]=val;
f[Size]=y,son[y][]=Size;
pushup(Size);
pushup(y);
pushup(x);
}
inline void change(int k,int val)
{
int x=rank(rt,k);
splay(x,);
s[x]=val;
pushup(x);
}
inline int bisearch(int kx,int ky)
{
int l=,r=n,mid;
while(l<=r)
{
mid=l+r>>;
if(ky+mid>n+)
{
r=mid-;
continue;
}
int x=rank(rt,kx-),y=rank(rt,kx+mid);
splay(x,),splay(y,x);
ll temp=hsh[son[y][]];
x=rank(rt,ky-),y=rank(rt,ky+mid);
splay(x,),splay(y,x);
if(temp==hsh[son[y][]])l=mid+;
else r=mid-;
}
return r;
}
}splay;
int main()
{
int m,i,j,k,x,y;
char op[],val[];
scanf("%s%d",str+,&m);
makepow();
n=strlen(str+);
splay.rt=splay.build(,n+,);
for(i=;i<=m;i++)
{
scanf("%s",op);
if(op[]=='I')
{
scanf("%d%s",&x,val);
splay.insert(x+,val[]);
n++;
}
else if(op[]=='R')
{
scanf("%d%s",&x,val);
splay.change(x+,val[]);
}
else
{
scanf("%d%d",&x,&y);
if(x>y) swap(x,y);
if(x!=y)
printf("%d\n",splay.bisearch(x+,y+));
else
printf("%d\n",n-x+);
}
}
return ;
}
bzoj1014火星人的更多相关文章
- 无旋Treap - BZOJ1014火星人 & 可持久化版文艺平衡树
!前置技能&概念! 二叉搜索树 一棵二叉树,对于任意子树,满足左子树中的任意节点对应元素小于根的对应元素,右子树中的任意节点对应元素大于根对应元素.换言之,就是满足中序遍历为依次访问节点对应元 ...
- BZOJ1014火星人prefix Splay維護序列 + 字符串哈希
@[Splay, 哈希] Description 火星人最近研究了一种操作:求一个字串两个后缀的公共前缀.比方说,有这样一个字符串:\(madamimadam\), 我们将这个字符串的各个字符予以标号 ...
- BZOJ1014 火星人的prefix
火星人最近研究了一种操作:求一个字串两个后缀的公共前缀.比方说,有这样一个字符串:madamimadam,我们将这个字符串的各个字符予以标号:序号: 1 2 3 4 5 6 7 8 9 10 11 字 ...
- bzoj1014 火星人 (hash+splay+二分答案)
求公共前缀的问题可以用hash+二分来解决,但这个是动态的,所以我们用平衡树来维护区间的hash值 复杂度$O(mlog^2n)$ #include<bits/stdc++.h> #def ...
- bzoj1000~1025
以后还是这样 25道题一起发 看着爽 noip失利之后发粪涂墙 刷了一波bzoj 题解: bzoj1000 A+B问题 这题不同的人有不同的写法,我写了个线段树套Treap,应该还是挺简单的 但是看别 ...
- [BZOJ1014][JSOI2008]火星人prefix
[BZOJ1014][JSOI2008]火星人prefix 试题描述 火星人最近研究了一种操作:求一个字串两个后缀的公共前缀.比方说,有这样一个字符串:madamimadam,我们将这个字符串的各个字 ...
- 【BZOJ1014】火星人(Splay,哈希)
[BZOJ1014]火星人(Splay,哈希) 题面 BZOJ 题解 要动态维护这个串,一脸的平衡树. 那么用\(Splay\)维护这个哈希值就好了. 每次计算答案的时候二分+Splay计算区间哈希值 ...
- BZOJ1014 JSOI2008 火星人prefix 【非旋转Treap】*
BZOJ1014 JSOI2008 火星人prefix Description 火星人最近研究了一种操作:求一个字串两个后缀的公共前缀.比方说,有这样一个字符串:madamimadam,我们将这个字符 ...
- 【bzoj1014】: [JSOI2008]火星人prefix 平衡树-字符串-hash-二分
[bzoj1014]: [JSOI2008]火星人 用平衡树维护字符串的hash 然后询问的时候二分一下就好了 /* http://www.cnblogs.com/karl07/ */ #includ ...
随机推荐
- String、StringBuilder、 StringBuffer 深入分析 源代码解析
java学习有一段时间了.但学习的东西都是框架等东西,java基础知识有点遗忘.所以重温一下java基础知识.写写文章里面有错的希望大家指正共同进步~~ 一.String 大家常常会说使用" ...
- 如何使用subversion管理iOS源代码
本文转载至 http://2009315319.blog.51cto.com/701759/819216 使用subversion管理iOS源代码 1.安装和配置subversion服务器 在wind ...
- Sitemesh3的使用心得
项目中用到了sitemesh3,就把使用心得记下来,至于配置之类的,官方网站都有,这里只是写下自己对它的理解,方便再次理解, sitemesh是基于过滤器的原理,拦截到符合配置文件中配置的路径,然后会 ...
- Earth Hour(最短路)
Earth Hour Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 125536/65536 K (Java/Others)Total ...
- VS2017生成类库选择Release失效的问题
VS的生成可以选择Debug模式或者Release模式,但是我发现在配置里面选择Release无效. 后来发现应该 在 生成->配置管理器 里面设置.
- [php][随机数]曲线式的随机
数学函数原型: y = max / (x ^ 2) 函数图像(来自google): y = 100 / x ^ (-2) 其中y为随机结果,max为最大值且max>1,x为随机数, 两个参数: ...
- 我的Android进阶之旅------>android:drawableLeft的用法
有时候想在EditText左边放一个图片,如图所示: 就可以在xml布局文件中的EditText定义代码中,添加入下面的代码,即可实现: android:drawableLeft="@dra ...
- Dubbo,ZooKeeper,Redis,FastDFS,ActiveMQ,Keepalived,Nginx,Hudson
获取[下载地址] QQ: 313596790 [免费支持更新] 三大数据库 mysql oracle sqlsever 更专业.更强悍.适合不同用户群体 [新录针对本系统的视频教程,手 ...
- 批处理设置IP地址
echo offecho 修改[本地连接]IP......netsh interface IP set address "本地连接" static 138.8.8.111 255. ...
- iOS UITableView滚动头图 拉伸放大效果 (头部弹性效果) 增加iOS11支持 附有demo
今天修改日期为2017年11月25日 两个月前做了iOS11的bug修复,才对博客进行更新,见谅. 在iOS11上需要注意两个问题 1.使用UIScrollview,UITableView,UIWeb ...