1. #define _CRT_SECURE_NO_WARNINGS
  2. #include<cmath>
  3. #include<iostream>
  4. #include<stdio.h>
  5. #include<algorithm>
  6. #include<map>
  7. #include<string.h>
  8. using namespace std;
  9. #define rep(i,t,n) for(int i =(t);i<=(n);++i)
  10. #define per(i,n,t) for(int i =(n);i>=(t);--i)
  11. #define mmm(a,b) memset(a,b,sizeof(a))
  12. #define ls(n) node[n].ch[0]
  13. #define rs(n) node[n].ch[1]
  14. const int N = ;
  15. const int INF = 0x3f3f3f3f;
  16.  
  17. struct Splay {
  18. struct Node {
  19. int fa, ch[];
  20. bool flip;
  21. int v, add, maxn, s;
  22. void init(int val)
  23. {
  24. v = maxn = val;
  25. s = ;
  26. add = flip = ch[] = ch[] = ;
  27. }
  28. }node[N];
  29. int root;
  30. //维护一个结点
  31. void pushup(int n)
  32. {
  33. node[n].maxn = max(node[n].v, max(node[ls(n)].maxn, node[rs(n)].maxn));
  34. node[n].s = node[ls(n)].s + node[rs(n)].s + ;
  35. }
  36. //标记向下传
  37. void pushdown(int n)
  38. {
  39. if (n == ) return;
  40. if (node[n].add) {
  41. if (ls(n)) {
  42. node[ls(n)].v += node[n].add;
  43. node[ls(n)].maxn += node[n].add;
  44. node[ls(n)].add += node[n].add;
  45. }
  46. if (rs(n)) {
  47. node[rs(n)].v += node[n].add;
  48. node[rs(n)].maxn += node[n].add;
  49. node[rs(n)].add += node[n].add;
  50. }
  51. node[n].add = ;
  52. }
  53. if (node[n].flip) {
  54. if (ls(n)) node[ls(n)].flip ^= ;
  55. if (rs(n)) node[rs(n)].flip ^= ;
  56. swap(ls(n), rs(n));
  57. node[n].flip = ;
  58. }
  59. }
  60. //旋转
  61. void rotate(int n, int d)
  62. {
  63. int fn = node[n].fa;
  64. int ffn = node[fn].fa;
  65. node[fn].ch[d ^ ] = node[n].ch[d];
  66. node[node[n].ch[d]].fa = fn;
  67.  
  68. node[n].ch[d] = fn;
  69. node[fn].fa = n;
  70.  
  71. node[ffn].ch[rs(ffn) == fn] = n;
  72. node[n].fa = ffn;
  73. pushup(fn);
  74. }
  75. //将结点n转到goal下
  76. void splay(int n, int goal)
  77. {
  78. while (node[n].fa != goal)
  79. {
  80. int fn = node[n].fa;
  81. int ffn = node[fn].fa;
  82. pushdown(ffn), pushdown(fn), pushdown(n);
  83. bool d = (ls(fn) == n);
  84. bool d1 = (ls(ffn) == fn);
  85. if (ffn == goal) rotate(n, d);
  86. else
  87. {
  88. if (d == d1) rotate(fn, d1); else rotate(n, d);
  89. rotate(n, d1);
  90. }
  91. }
  92. pushup(n);
  93. if (goal == ) root = n;
  94. }
  95. //找寻中序遍历中的第pos个结点
  96. int select(int pos)
  97. {
  98. int u = root;
  99. pushdown(u);
  100. while (node[ls(u)].s != pos)
  101. {
  102. if (pos < node[ls(u)].s) u = ls(u);
  103. else
  104. {
  105. pos -= node[ls(u)].s + ;
  106. u = rs(u);
  107. }
  108. pushdown(u);
  109. }
  110. return u;
  111. }
  112. //查询l~r最大值
  113. int query(int l, int r)
  114. {
  115. int u = select(l - ), v = select(r + );
  116. splay(u, ); splay(v, u);
  117. return node[ls(v)].maxn;
  118. }
  119. //给l~r加上val
  120. void update(int l, int r, int val)
  121. {
  122. int u = select(l - ), v = select(r + );
  123. splay(u, ); splay(v, u);
  124. node[ls(v)].v += val;
  125. node[ls(v)].maxn += val;
  126. node[ls(v)].add += val;
  127. }
  128. //翻转l~r
  129. void reverse(int l, int r)
  130. {
  131. int u = select(l - ), v = select(r + );
  132. splay(u, ); splay(v, u);
  133. node[ls(v)].flip ^= ;
  134. }
  135. //类似二分来建树,就是这段代码现在的我还不会用指针来替换
  136. int build(int l, int r)
  137. {
  138. if (l > r) return ;
  139. if (l == r) return l;
  140. int mid = (l + r) >> ;
  141. int L, R;
  142. ls(mid) = L = build(l, mid - );
  143. rs(mid) = R = build(mid + , r);
  144. node[L].fa = node[R].fa = mid;
  145. pushup(mid);
  146. return mid;
  147. }
  148. //初始化
  149. void init(int n)
  150. {
  151. node[].init(-INF); node[].s = ;
  152. node[].init(-INF);
  153. node[n + ].init(-INF);
  154. for (int i = ; i <= n + ; i++)
  155. node[i].init();
  156. root = build(, n + );
  157. node[root].fa = node[].fa = ;
  158. ls() = root;
  159. }
  160. }splay_tree;
  161.  
  162. int main()
  163. {
  164. int n, m;
  165. scanf("%d%d", &n, &m);
  166. splay_tree.init(n);
  167. for (int i = ; i < m; i++)
  168. {
  169. int opt, l, r, v;
  170. scanf("%d%d%d", &opt, &l, &r);
  171. if (opt == ) { scanf("%d", &v); splay_tree.update(l, r, v); }
  172. if (opt == ) splay_tree.reverse(l, r);
  173. if (opt == ) printf("%d\n", splay_tree.query(l, r));
  174. }
  175. return ;
  176. }
  177. /*
  178. const int maxn = 55;
  179. const int inf = 1e9 + 5;
  180. ll n,m;
  181. struct splay_tree {
  182. struct node {
  183. int val, mx, add, sz, son[2];
  184. bool rev;
  185. void init(int _val) { val = mx = _val, sz = 1, add = rev = son[0] = son[1]; }
  186. }T[maxn];
  187. int fa[maxn], root;
  188.  
  189. void Rotate(int x, int kind) {
  190. int y = fa[x], z = fa[y];
  191. T[y].son[!kind] = T[x].son[kind], fa[T[x].son[kind]] = y;
  192. T[x].son[kind] = y, fa[y] = x;
  193. T[z].son[T[z].son[1] == y] = x, fa[x] = z;//orz
  194. }
  195. void Splay(int x,)
  196. };
  197. string s[maxn];
  198. map<char, int> mmp;
  199.  
  200. int main()
  201. {
  202. cin >> n >> m;
  203. hehe.init();
  204. for (int i = 0, a, b, c, d; i < m; i++) {
  205. scanf("%d", &a);
  206. if (a == 1) { scanf("%d%d%d", &b, &c, &d); hehe.update(b, c, d); }
  207. else if (a == 2) { scanf("%d%d", &b, &c); hehe.Reverse(b, c); }
  208. else { scanf("%d%d", &b, &c); printf("%d\n"); hehe.query(b, c); }
  209. }
  210.  
  211. return 0;
  212. }*/

【待补】splay 模板的更多相关文章

  1. bzoj 1588 splay模板题

    用晚自习学了一下splay模板,没想象中那么难,主要是左旋和右旋可以简化到一个函数里边,减少代码长度... #include<iostream> #include<cstdio> ...

  2. COJ 1002 WZJ的数据结构(二)(splay模板)

    我的LCC,LCT,Splay格式终于统一起来了... 另外..这个形式的Splay是标准的Splay(怎么鉴别呢?看Splay函数是否只传了一个变量node就行),刘汝佳小白书的Splay写的真是不 ...

  3. Splay 模板

    Splay 模板 struct SplayTree{ const static int maxn = 1e5 + 15; int ch[maxn][2] , key[maxn] , s[maxn] , ...

  4. [luogu3369/bzoj3224]普通平衡树(splay模板、平衡树初探)

    解题关键:splay模板题整理. 如何不加入极大极小值?(待思考) #include<cstdio> #include<cstring> #include<algorit ...

  5. BZOJ1588 [HNOI2002]营业额统计 splay模板

    1588: [HNOI2002]营业额统计 Time Limit: 5 Sec  Memory Limit: 162 MB Submit: 16189  Solved: 6482 [Submit][S ...

  6. 文艺平衡树(splay模板)

    题干:splay模板,要求维护区间反转. splay是一种码量小于treap,但支持排名,前驱后继等treap可求的东西,也支持区间反转的平衡树. 但是有两个坏处: 1.splay常数远远大于trea ...

  7. [洛谷P3391] 文艺平衡树 (Splay模板)

    初识splay 学splay有一段时间了,一直没写...... 本题是splay模板题,维护一个1~n的序列,支持区间翻转(比如1 2 3 4 5 6变成1 2 3 6 5 4),最后输出结果序列. ...

  8. bzoj 1208 splay模板题2

    自己yy了找前驱和后继,学了学怎么删除...(反正就是练模板) #include<iostream> #include<cstdio> #include<cstring& ...

  9. 【BZOJ 3196】二逼平衡树 线段树套splay 模板题

    我写的是线段树套splay,网上很多人写的都是套treap,然而本蒟蒻并不会treap 奉上sth神犇的模板: //bzoj3196 二逼平衡树,支持修改某个点的值,查询区间第k小值,查询区间某个值排 ...

随机推荐

  1. JAVA代码实现多级树结构封装对象

    树结构在开发中经常遇到.例如:部门.菜单.员工架构等等.下面用部门作为例子构造部门结构树 1.部门表:dept -- ---------------------------- -- Table str ...

  2. Kubernetes1.2如何使用iptables

    转:http://blog.csdn.net/horsefoot/article/details/51249161 本次分析的kubernetes版本号:v1.2.1-beta.0. Kubernet ...

  3. JAVA 线程池架构浅析

    经历了Java内存模型.JUC基础之AQS.CAS.Lock.并发工具类.并发容器.阻塞队列.atomic类后,我们开始JUC的最后一部分:线程池.在这个部分你将了解到下面几个部分: 线程池的基础架构 ...

  4. File 类的 getCanonicalFile( ) 和 getAbsoluteFile( ) 区别

    一.打开java.io.File源码,看下两个方法的区别 getAbsoluteFile public File getAbsoluteFile() { String absPath = getAbs ...

  5. git push origin master和git push有什么区别?

    1.master是主分支,还可以建一些其他的分支用于开发.2.git push origin master的意思就是上传本地当前分支代码到master分支.git push是上传本地所有分支代码到远程 ...

  6. linux选择sdb sdb4 fat32 还是sda分区

    fat32是怎么混到它们中的sda,sdb,sdc是你的第一块,第二块,第三块硬盘sda1,sda2,sda5是你第一块硬盘中的第一块分区,2块,5块分区fat32,ext2,ext3,ext4是你的 ...

  7. 浅析C#中的结构体和类

    类和结构是 .NET Framework 中的常规类型系统的两种基本构造. 两者在本质上都属于数据结构.封装着一组总体作为一个逻辑单位的数据和行为. 数据和行为是该类或结构的"成员" ...

  8. 一个Login页面全面了解session与cookie

    背景 做了四年的前端开发,对外一直说自己是web开发,那么身为一个web开发怎能不知道session与cookie以及其管理方式呢~ Login涉及技术栈:Nodejs,MongoDB,Express ...

  9. 解决java.sql.SQLException: The server time zone value 'Öйú±ê׼ʱ¼ä' is unrecognized or represents more than one time zone

    使用spring boot整合MySQL时一直报 java.sql.SQLException: The server time zone value 'Öйú±ê׼ʱ¼ä' is unrecog ...

  10. Python默认参数的坑

    默认参数的坑 定义一个函数,传入一个list,添加一个end再返回 def add_end(L=[]): L.append('END') return L 正常调用时,结果似乎不错 print add ...