【算法】splay

【题解】对于每个结点维护其子树串的hash值,前面为高位,后面为低位。

sum[x]=sum[L]*base[s[R]+1]+A[x]*base[s[R]]+sum[R],其中sum为哈希,base为乘权,A为数值(即字符)。

#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int maxn=,inf=0x3f3f3f3f,bases=;
int f[maxn],t[maxn][],s[maxn],A[maxn],a[maxn],sz=,root,n;
unsigned long long sum[maxn],a_,b_,b[maxn];
int Node(int fa,int num)
{
sz++;
f[sz]=fa;t[sz][]=t[sz][]=;
s[sz]=;A[sz]=sum[sz]=num;
return sz;
}
void count(int x)
{
s[x]=s[t[x][]]++s[t[x][]];
sum[x]=sum[t[x][]]*b[s[t[x][]]+]+1ull*A[x]*b[s[t[x][]]]+sum[t[x][]];
}
void build(int fa,int &x,int l,int r)
{
if(l>r)return;
int mid=(l+r)>>;
x=Node(fa,a[mid]);
build(x,t[x][],l,mid-);
build(x,t[x][],mid+,r);
count(x);
}
void rotate(int x)
{
int k=x==t[f[x]][];
int y=f[x];
t[y][k]=t[x][!k];f[t[x][!k]]=y;
if(f[y])t[f[y]][y==t[f[y]][]]=x;f[x]=f[y];f[y]=x;
t[x][!k]=y;
sum[x]=sum[y];s[x]=s[y];
count(y);
}
void splay(int x,int r)
{
for(int fa=f[r];f[x]!=fa;)
{
if(f[f[x]]==fa){rotate(x);return;}
int X=x==t[x][],Y=f[x]==t[f[f[x]]][];
if(X^Y)rotate(x),rotate(x);
else rotate(f[x]),rotate(x);
}
}
void find(int &x,int k)
{
for(int i=x;i;)
{
if(k<=s[t[i][]]){i=t[i][];continue;}
if(k==s[t[i][]]+){splay(i,x);x=i;return;}
k-=s[t[i][]]+;i=t[i][];
}
}
bool work(int x,int y,int longs)
{
if(x+longs->n||y+longs->n)return ;
find(root,x);find(t[root][],longs+);
a_=sum[t[t[root][]][]];
find(root,y);find(t[root][],longs+);
b_=sum[t[t[root][]][]];
if(a_==b_)return ;
return ;
}
void ask()
{
int x,y;
scanf("%d%d",&x,&y);
int l=,r=maxn;
while(l<r)
{
int mid=(l+r)>>;
if(work(x,y,mid))l=mid+;
else r=mid;
}
printf("%d\n",l-);
}
void repair()
{
int x;char c;
scanf("%d %c",&x,&c);
find(root,x+);
A[root]=c-'a'+;
count(root);
}
void insert()
{
n++;
int x;char c;
scanf("%d %c",&x,&c);
find(root,x+);find(t[root][],);
int y=Node(t[root][],c-'a'+);
t[t[root][]][]=y;
f[y]=t[root][];
count(t[root][]);
count(root);
}
char str[maxn];
int main()
{
scanf("%s",str+);
n=strlen(str+);
for(int i=;i<=n;i++)a[i]=str[i]-'a'+;
b[]=;
for(int i=;i<=maxn;i++)b[i]=b[i-]*bases;
root=a[]=a[n+]=;
build(,root,,n+);
int m;
scanf("%d",&m);
for(int i=;i<=m;i++)
{
scanf("%s",str);//不要用%c会读空格,用%s读到空格会停。
if(str[]=='Q')ask();
if(str[]=='R')repair();
if(str[]=='I')insert();
}
return ;
}

update:现在已改用fhq-treap代替splay。

【BZOJ】1014 [JSOI2008]火星人prefix的更多相关文章

  1. BZOJ 1014: [JSOI2008]火星人prefix [splay 二分+hash] 【未完】

    1014: [JSOI2008]火星人prefix Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 6243  Solved: 2007[Submit] ...

  2. BZOJ 1014: [JSOI2008]火星人prefix Splay+二分

    1014: [JSOI2008]火星人prefix 题目连接: http://www.lydsy.com/JudgeOnline/problem.php?id=1014 Description 火星人 ...

  3. bzoj 1014: [JSOI2008]火星人prefix hash && splay

    1014: [JSOI2008]火星人prefix Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 3154  Solved: 948[Submit][ ...

  4. 求帮看!!!!BZOJ 1014 [JSOI2008]火星人prefix

    1014: [JSOI2008]火星人prefix Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 4164  Solved: 1277[Submit] ...

  5. BZOJ 1014: [JSOI2008]火星人prefix( splay + hash )

    用splay维护序列, 二分+hash来判断LCQ.. #include<bits/stdc++.h> using namespace std; typedef unsigned long ...

  6. BZOJ 1014 [JSOI2008]火星人prefix (Splay + Hash + 二分)

    1014: [JSOI2008]火星人prefix Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 8112  Solved: 2569[Submit] ...

  7. [BZOJ 1014] [JSOI2008] 火星人prefix 【Splay + Hash】

    题目链接:BZOJ - 1014 题目分析 求两个串的 LCP ,一种常见的方法就是 二分+Hash,对于一个二分的长度 l,如果两个串的长度为 l 的前缀的Hash相等,就认为他们相等. 这里有修改 ...

  8. BZOJ 1014: [JSOI2008]火星人prefix

    Sol Splay+Hash+二分答案. 用Splay维护Hash,二分答案判断. 复杂度 \(O(nlog^2n)\) PS:这题调了两个晚上因为没开long long.许久不写数据结构题感觉写完整 ...

  9. bzoj 1014 [JSOI2008]火星人prefix(splay+hash)

    [题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=1014 [题意] 给定一个字符串,要求提供修改一个字符,插入一个字符,查询两个后缀LCP ...

  10. bzoj 1014 [JSOI2008]火星人prefix——splay+哈希

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=1014 用splay维护字符串,每个点记录子树的哈希值,然后二分查询. 二分不是把两个点的哈希 ...

随机推荐

  1. Response.End方法

    文章:在try...catch语句中执行Response.End()后如何停止执行catch语句中的内容 调用Response.End()方法能保证,只输出End方法之前的内容. 调用Context. ...

  2. Alpha-5

    前言 失心疯病源5 团队代码管理github 站立会议 队名:PMS 530雨勤(组长) 今天完成了那些任务 14:30~15:30 阅读blob分析相关论文,找到一篇很早年的论文,但是作者讲解十分细 ...

  3. Chrome 的扩展功能

    chrome浏览器修改cookie edit this cookie chrome插件是一款专为谷歌内核浏览器打造的cookie插件,安装谷歌浏览器edit this cookie插件后你就可以在浏览 ...

  4. ExtremeComponents源码解析(一)

    一.前言 因参与公司框架改造,在负责前端table组件选型时,原本选了jqGrid和Bootstraptable作为备选方案,评审会上,武哥提了EXtremeComponents,让我也去了解下,看下 ...

  5. java 写入int型时会自动转换成字符

    java  写入int型时会自动转换成字符

  6. 【bzoj2588】Spoj 10628. Count on a tree 离散化+主席树

    题目描述 给定一棵N个节点的树,每个点有一个权值,对于M个询问(u,v,k),你需要回答u xor lastans和v这两个节点间第K小的点权.其中lastans是上一个询问的答案,初始为0,即第一个 ...

  7. BZOJ4868 Shoi2017期末考试(三分+贪心)

    容易想到枚举最晚发布成绩的课哪天发布,这样与ti和C有关的贡献固定.每门课要么贡献一些调节次数,要么需要一些调节次数,剩下的算贡献也非常显然.这样就能做到平方级别了. 然后大胆猜想这是一个凸函数三分就 ...

  8. struts2远程代码执行漏洞汇总整理

    一.S2-001 1.漏洞原理 在默认配置下,如果用户所提交的表单出现验证错误,后端会对用户的输入进行解析处理,然后返回并显示处理结果. 举个例子,当你提交的登录表单为username=xishir& ...

  9. Spring.NET中事务管理【转】

    http://www.cnblogs.com/GoodHelper/archive/2009/11/16/springnet_transaction.html 浏览了下写的比较清楚. 在.NET FC ...

  10. redux的一些插件总结(redux-actions,reselect)

    redux本身还是过于简单,实际使用的时候需要配合许多插件. 下面是一些插件与vuex的功能对比 redux-actions <=> vuex的mutation的写法 reselect & ...