ZKW Splay

原创 2016年08月29日 20:58:18

来宣传我大ZKW Splay.

没错这就是我说的Splay的奇怪姿势,貌似很少人知道?

据某论文所说常数是一般Splay的一半(没记错的话233).


大多数Splay自底向上,而我大ZKW Splay自顶向下.

基本操作是“zig”和“zigzig”,分别为“单旋”和“双旋”.

核心操作为search,select,所有的操作在root点展开.

search是在树上查找满足大小条件的一个点.

search时,从根节点向下走,之前经过的点,连同它的另一子树,都挂到一个链表上(像晾毛巾一样).

当根节点为要找的点时,停下来,这时候暴力把晾起来的“毛巾”挂回去.


select是在树上查找第k大的点.

原理和search相似.


用神奇的缩行可以把行数压在八、九十行(附带插入删除第k大).

由于,每次search,select操作会使树的形态发生变化,所以不能可持久化.

虽然自顶向下但也可以支持LCT.


最后 :

onst int oo=(1LL << 31)-1;
struct node {
	int key,size;
	node *c[2];
	node(): key(0),size(0){c[0]=c[1]=this;}
	node(int kk,node* c0,node* c1): key(kk){c[0]=c0;c[1]=c1;}
	node* rz() {return size=c[0]->size+c[1]->size+1,this;	}
}Tnull,*null=&Tnull;
node *last[2];
struct splay {
	node *root;
	splay() {
		root=(new node(*null))->rz();
		root->key=oo;
	}
	void zig(bool w) {
		last[w]=root;
		node *t=root->c[w];
		root->c[w]=null->c[w];
		null->c[w]=root;
		root=t;
	}
	void zigzig(bool w) {
		last[w]=root->c[w];
		node *t=root->c[w]->c[w];
		root->c[w]->c[w]=null->c[w];
		null->c[w]=root->c[w];
		root->c[w]=null->c[w]->c[!w];
		null->c[w]->c[!w]=root->rz();
		root=t;
	}
	void finish(bool w) {
		node *t=null->c[w],*p=root->c[!w];
		while (t!=null) {
			t=null->c[w]->c[w];
			null->c[w]->c[w]=p;
			p=null->c[w]->rz();
			null->c[w]=t;
		}
		root->c[!w]=p;
	}
	void select(int k) {
		int t;
		for (;;) {
			bool w=k>(t=root->c[0]->size);
			if (k==t|| root->c[w]==null) break;
			if (w) k-=t+1;
			bool ww=k>(t=root->c[w]->c[0]->size);
			if (k==t || root->c[w]->c[ww]==null) {zig(w);break;}
			if (ww) k-=t+1;
			w!=ww?zig(w),zig(ww):zigzig(w);
		}
		finish(0),finish(1);
		root->rz();
	}
	void search(int x) {
		for (;;) {
			bool w=x>root->key;
			if (root->c[w]==null) break;
			bool ww=x>root->c[w]->key;
			if (root->c[w]->c[ww]==null) {zig(w);break;}
			w!=ww?zig(w),zig(ww):zigzig(w);
		}
		finish(0); finish(1);
		root->rz();
		if (x>root->key) select(root->c[0]->size+1);
	}
	void ins(int x) {
		search(x);
		node *oldroot=root;
		root=new node(x,oldroot->c[0],oldroot);
		oldroot->c[0]=null;
		oldroot->rz();
		root->rz();
	}
	void del(int x) {
		search(x);
		node *oldroot=root;
		root=root->c[1];
		select(0);
		root->c[0]=oldroot->c[0];
		root->rz();
		delete oldroot;
	}
	int sel(int k) {return select(k-1),root->key;}
	int ran(int x) {return search(x),root->c[0]->size+1;}
};


最最后,orz ZKW.


版权声明:本文为博主原创文章,未经博主允许不得转载。

zkw线段树详解

转载自:http://blog.csdn.net/qq_18455665/article/details/50989113 前言 首先说说出处:清华大学 张昆玮(zkw) - ppt 《统计的力...
  • keshuqi
  • keshuqi
  • 2016年08月14日 19:35
  • 5307

ZKW Splay

来宣传我大ZKW Splay.
  • GE__he
  • GE__he
  • 2016年08月29日 20:58
  • 757

Splay基本操作和线段树(指针版)

splay 线段树splay#include #include #include #include #include #include #include #define fo(i,a,b) for(i...
  • Lifel
  • Lifel
  • 2017年08月07日 20:17
  • 133

zkw Splay学习笔记

最近。。 最近心里颇不平静。 最近花了三天时间学了zkw Splay,发现这玩意儿真TM难写;加上各种Code Trick也还是写了好久,还有各种错误,一直在炸。 一些心得: ①维护size时不需...
  • TA201314
  • TA201314
  • 2015年01月12日 21:45
  • 1023

最小费用最大流之 zkw费用流与普通费用流

http://www.artofproblemsolving.com/blog/54262 这个是原作者的博文地址 这是今天刚学的,不过理解上还是很浅薄。最近发现算法不能融会贯通还是因为自己太死板...
  • sdj222555
  • sdj222555
  • 2012年08月08日 01:38
  • 9282

zkw线段树

zkw线段树
  • unicornt_
  • unicornt_
  • 2016年07月31日 14:05
  • 406

Linux LVM逻辑卷错误恢复一例

使用LVM建立了一个逻辑卷为/dev/mapper/test-test。由于异常关机,造了逻辑卷错误,无法挂载。 于是检查逻辑卷,提示:# fsck.ext3 -f /dev/mapper/test-...
  • vah101
  • vah101
  • 2011年04月15日 14:58
  • 10775

[BZOJ3196]二逼平衡树(线段树套splay)

花费了不知多少页来描述我们的心情 却不知为何填不满一行的空白
  • Clove_unique
  • Clove_unique
  • 2016年04月29日 09:59
  • 1840

ZKW线段树

题目:敌兵布阵   题意:给一个数组,然后有一系列操作:(1)把某一个值加上一个数,(2)把某一个值减去一个数,(3)求一段区间的和。 #include #include #include u...
  • ACdreamers
  • ACdreamers
  • 2013年08月31日 10:41
  • 5647

zkw线段树解决区间rmq

zkw线段树具体内容请百度统计的力量(这是他讲的时候所用的ppt的名字)
  • u012513980
  • u012513980
  • 2014年05月22日 23:47
  • 2063
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:ZKW Splay
举报原因:
原因补充:

(最多只允许输入30个字)