及其简短的Splay代码
#include <stdio.h>
#include <queue>
#include <algorithm>
#include <stdlib.h>
#include <math.h>
#include <iostream>
#define inf 1000000000
using namespace std;
#define getch() getchar()
inline int F() {register int aa , bb , ch;
while(ch = getch() , (ch<''||ch>'') && ch != '-'); ch == '-' ? aa=bb= : (aa=ch-'',bb=);
while(ch = getch() , ch>=''&&ch<='') aa = aa* + ch-''; return bb ? aa : -aa;
}
const int Maxn = ;
queue<int> q;
int n , m , root , sz;
int fa[Maxn] , c[Maxn][] , mx[Maxn] , lx[Maxn] , rx[Maxn] , v[Maxn] , size[Maxn] , sum[Maxn] , a[Maxn] , id[Maxn];
bool lazy[Maxn] , rev[Maxn]; void update(int x) {
int lc = c[x][] , rc = c[x][];
sum[x] = sum[lc] + sum[rc] + v[x];
size[x] = size[lc] + size[rc] + ;
mx[x] = max(mx[lc] , mx[rc]);
mx[x] = max(mx[x] , rx[lc]+v[x]+lx[rc]);
lx[x] = max(lx[lc] , sum[lc] + v[x] + lx[rc]);
rx[x] = max(rx[rc] , sum[rc] + v[x] + rx[lc]);
} void downpush(int x) {
int lc = c[x][] , rc = c[x][];
if(lazy[x]) {
rev[x] = lazy[x] = ;
if(lc) lazy[lc] = , v[lc] = v[x] , sum[lc] = v[x]*size[lc];
if(rc) lazy[rc] = , v[rc] = v[x] , sum[rc] = v[x]*size[rc];
if(v[x] >= ) {
if(lc) lx[lc] = rx[lc] = mx[lc] = sum[lc];
if(rc) lx[rc] = rx[rc] = mx[rc] = sum[rc];
}
else {
if(lc) lx[lc] = rx[lc] = , mx[lc] = v[x];
if(rc) lx[rc] = rx[rc] = , mx[rc] = v[x];
}
}
if(rev[x]) {
rev[x] = ;
rev[lc] ^= ;
rev[rc] ^= ;
swap(lx[lc] , rx[lc]);
swap(lx[rc] , rx[rc]);
c[x][] = rc;
c[x][] = lc;
swap(lx[x] , rx[x]);
}
} void rotate(int&root , int x) {
int y = fa[x] , z = fa[y] , p , q;
if(x == c[y][]) p = ; else p = ;
q = p^;
if(y == root) root = x;
else {
if(c[z][] == y) c[z][] = x;
else c[z][] = x;
}
fa[x] = z; fa[y] = x; fa[c[x][q]] = y;
c[y][p] = c[x][q]; c[x][q] = y;
update(y); update(x);
}
void splay(int&root , int x) {
int y , z;
while(x != root) {
y = fa[x] , z = fa[y];
if(y != root) {
if((x == c[y][]) ^ (y == c[z][])) rotate(root , x);
else rotate(root , y);
}
rotate(root , x);
}
} int find(int x , int rk) {
downpush(x);
int lc = c[x][] , rc = c[x][];
if(size[lc] + == rk) return x;
if(size[lc] >= rk) return find(lc , rk);
else return find(rc , rk-size[lc]-);
} void rec(int x) {
if(!x) return ;
int lc = c[x][] , rc = c[x][];
rec(lc);rec(rc);q.push(x);
fa[x] = c[x][] = c[x][] = lazy[x] = rev[x] = ;
} int split(int k , int tot) {
int x = find(root , k);
splay(root , x);
x = find(root , k+tot+);
splay(c[root][] , x);
return c[ c[root][] ][];
} void query(int k , int tot) {
int x = split(k , tot);
printf("%d\n",sum[x]);
} void modify(int k , int tot , int val) {
int x = split(k , tot) , y = fa[x];
v[x] = val; lazy[x] = ; sum[x] = size[x]*val;
if(val >= ) lx[x] = rx[x] = mx[x] = sum[x];
else lx[x] = rx[x] = , mx[x] = val;
update(y); update(fa[y]);
} void reverse(int k , int tot) {
int x = split(k , tot);
if(!lazy[x]) {
rev[x] ^= ;
downpush(x);
update(fa[x]);
update(fa[fa[x]]);
}
} void erase(int k , int tot) {
int x = split(k , tot) , y = fa[x];
rec(x); c[y][] = ;
update(y); update(fa[y]);
}
void build(int l,int r,int f)
{
if(l>r)return;
int mid=(l+r)>>,now=id[mid],last=id[f];
if(l==r)
{
sum[now]=a[l];size[now]=;
lazy[now]=rev[now]=;
if(a[l]>=)lx[now]=rx[now]=mx[now]=a[l];
else lx[now]=rx[now]=,mx[now]=a[l];
}
else build(l,mid-,mid),build(mid+,r,mid);
v[now]=a[mid];fa[now]=last;update(now);
c[last][mid>=f]=now;
}
void insert(int k,int tot)
{
for(int i=;i<=tot;i++)a[i]=F();
for(int i=;i<=tot;i++)
if(!q.empty())id[i]=q.front(),q.pop();
else id[i]=++sz;
build(,tot,);int z=id[(+tot)>>];
int x=find(root,k+),y=find(root,k+);
splay(root,x);splay(c[x][],y);
fa[z]=y;c[y][]=z;
update(y);update(x);
} int main() {
n = F(); m = F();
mx[] = a[] = a[n+] = -inf;
for(int i=; i<=n; ++i) {
a[i+] = F();
}
for(int i=;i<=n+;i++)id[i]=i;
build(,n+,);
root = (n+) >> ;sz = n + ;
int k , tot , val;
char ch[];
while(m--) {
scanf("%s",ch);
if(ch[]!='M' || ch[] != 'X') k = F() , tot = F();
if(ch[] == 'I') insert(k , tot);
if(ch[] == 'D') erase(k , tot);
if(ch[] == 'M') {
if(ch[] == 'X') printf("%d\n",mx[root]);
else val = F() , modify(k , tot , val);
}
if(ch[] == 'R') reverse(k , tot);
if(ch[] == 'G') query(k , tot);
}
}
Splay的核心操作
void rotate(int&root , int x) {
int y = fa[x] , z = fa[y] , p , q;
if(x == c[y][]) p = ; else p = ;
q = p^;
if(y == root) root = x;
else {
if(c[z][] == y) c[z][] = x;
else c[z][] = x;
}
fa[x] = z; fa[y] = x; fa[c[x][q]] = y;
c[y][p] = c[x][q]; c[x][q] = y;
update(y); update(x);
}
void splay(int&root , int x) {
int y , z;
while(x != root) {
y = fa[x] , z = fa[y];
if(y != root) {
if((x == c[y][]) ^ (y == c[z][])) rotate(root , x);
else rotate(root , y);
}
rotate(root , x);
}
}
及其简短的Splay代码的更多相关文章
- Splay代码简化版
皆さん.こんにちは.上一篇文章,我们讲了Splay如何实现.这一篇我们来让我们的伸展树短一点. 上一篇Splay讲解的链接:リンク. 首先还是变量的定义,在这里呢,我把一些小函数也用Define来实现 ...
- 普通平衡树与文艺平衡树的splay代码
主要综合借鉴了yyb和马前卒两位大佬的. //普通平衡树 #include <cstdio> #include <cctype> #include <cstring> ...
- 将近半个小时,把一小段简短的汇编代码写成了C语言代码
我自己看,感觉好像一句一句翻译的,写得很是生硬,不如书上写的灵活 0040137E 8B7424 04 MOV ESI,DWORD PTR SS:[ESP+4]00401382 ...
- 一个 11 行 Python 代码实现的神经网络
一个 11 行 Python 代码实现的神经网络 2015/12/02 · 实践项目 · 15 评论· 神经网络 分享到:18 本文由 伯乐在线 - 耶鲁怕冷 翻译,Namco 校稿.未经许可,禁止转 ...
- [C#] 用一种更优美的方式来替换掉又多又长的switch-case代码段
switch-case语句是我们编码过程中常用的一种分支语句.然而正所谓成也萧何败萧何,每当我们向一个已经拥有了成百上千行的switch-case代码段中添加新的case分支的时候,我们是否有过为代码 ...
- 如何把if-else代码重构成高质量代码
原文:https://blog.csdn.net/qq_35440678/article/details/77939999 本文提纲: 为什么我们写的代码都是if-else? 这样的代码有什么缺点? ...
- 算法笔记--Splay && Link-Cut-Tree
Splay 参考:https://tiger0132.blog.luogu.org/slay-notes 普通模板: ; ], val[N], cnt[N], fa[N], sz[N], lazy[N ...
- PHP 代码规范、流程规范、git规范
1. 命名规范 (1).变量命名规范 1.变量使用驼峰命名法 禁止使用拼音或者拼音加数字 2.变量也应具有描述性,杜绝一切拼音.或拼音英文混杂的命名方式 3.变量包数字.字母和下划线字符,不允许使用其 ...
- 【Luogu】P1486郁闷的出纳员(Splay)
题目链接 名副其实的调了一下午…… 每做一道题都是对我那不规范的Splay代码的刀刻斧凿一般的修正啊…… Splay.如果有一批员工不干了,那就找还能干的薪水最少的员工,把它splay到根,删除它的左 ...
随机推荐
- Unity3d 换装Avatar系统
原理就是用新造的部件和角色的骨骼进行重新对接. demo的使用方法: PartIdx设置要换那个部件[0,4],一共5个部件 EquipIdx设置要更换部件的装备索引[0,1],具体看我的Change ...
- ACM/ICPC 之 拓扑排序+DFS(POJ1128(ZOJ1083)-POJ1270)
两道经典的同类型拓扑排序+DFS问题,第二题较第一题简单,其中的难点在于字典序输出+建立单向无环图,另外理解题意是最难的难点,没有之一... POJ1128(ZOJ1083)-Frame Stacki ...
- 算法手记 之 数据结构(堆)(POJ 2051)
一篇读书笔记 书籍简评:<ACM/ICPC 算法训练教程>这本书是余立功主编的,代码来自南京理工大学ACM集训队代码库,所以小编看过之后发现确实很实用,适合集训的时候刷题啊~~,当时是听了 ...
- 【Android】如何将eclipse工程导入studio
1.eclipse工程右键->export->Generate Gradle build files 2.studio->New->import project->选择工 ...
- HDU 4865 Peter's Hobby(概率、dp、log)
给出2个影响矩阵,一个是当天天气对湿度的影响,一个是前一天天气对当天天气的影响. 即在晴天(阴天.雨天)发生Dry(Dryish.Damp.Soggy)的概率,以及前一天晴天(阴天.雨天)而今天发生晴 ...
- 【leetcode】Plus One (easy)
Given a non-negative number represented as an array of digits, plus one to the number. The digits ar ...
- LeetCode 459 Repeated Substring Pattern
Problem: Given a non-empty string check if it can be constructed by taking a substring of it and app ...
- 如何把一个excel工作薄中N个工作表复制到另一个工作薄中
一般遇到标题这样的情况,许多人可能会一个一个的复制粘贴,其实完全不必那么麻烦. 你可以按以下步骤来操作: 第一步:打开所有要操作的excel工作薄\n 第二步:按住Shift键,选择所有要复制的工作表 ...
- IIS配置默认文档
我们在配置IIS的默认文档时是在这里配置的,如下图: 但是,有可能我们的根目录下没有这个文件,而且我们网站运行的时候也不想访问根目录下的这个文件,而是要访问其他文件夹下的某一个文件,比如网站运行的时候 ...
- iphone删除自动更新的系统
1.利用 etc/host 文件屏蔽 Apple 更新服务器用电脑 iTools 或者手机 iFile 打开 etc/host 文件,添加:127.0.0.1 mesu.apple.com到文件中.2 ...