题意

给定$n$个数序列,每次两个操作,将区间$[L,R]$拼接到去掉区间后的第$c$个数后,或者翻转$[L,R]$


Splay区间操作模板,对于区间提取操作,将$L-1$ Splay到根,再将$R+1$ Splay到根节点的右儿子,那么根节点右儿子的左儿子就对应区间$[L,R]$,对于反转操作,通过懒操作下放

代码

#include <bits/stdc++.h>
#define inf 0x7f7f7f7f
using namespace std;
const int N = 500005;
int ch[N][2], fa[N], key[N], lazy[N], sz[N];
int root, tot;
inline int get(int x) {return ch[fa[x]][1] == x;} // left is 0, right is 1
inline void pushup(int x) {
sz[x] = sz[ch[x][0]] + sz[ch[x][1]] + 1;
}
inline void pushdown(int x) {
if(lazy[x]) {
lazy[x] = 0;
swap(ch[x][0], ch[x][1]);
lazy[ch[x][0]] ^= 1; lazy[ch[x][1]] ^= 1;
}
}
inline void rotate(int x) {
int f = fa[x], ff = fa[f], which = get(x);
pushdown(f); pushdown(x);
ch[f][which] = ch[x][which ^ 1];
fa[ch[f][which]] = f;
ch[x][which ^ 1] = f;
fa[f] = x; fa[x] = ff;
if(ff) ch[ff][ch[ff][1] == f] = x;
pushup(f); pushup(x);
}
inline void splay(int x, int target) {
while(fa[x] != target) {
if(fa[fa[x]] != target) {
rotate((get(x) == get(fa[x])) ? fa[x] : x);
}
rotate(x);
}
if(!target) root = x;
}
inline int get_kth(int x, int k) {
if(!x) return 0;
while(1) {
pushdown(x);
if(k == sz[ch[x][0]] + 1) break;
if(k > sz[ch[x][0]] + 1) {
k -= sz[ch[x][0]] + 1; x = ch[x][1];
}else x = ch[x][0];
}
return x;
}
inline int newnode(int v, int f) {
int x = ++tot;
ch[x][0] = ch[x][1] = 0; fa[x] = f;
key[x] = v; sz[x] = 1; lazy[x] = 0;
return x;
}
int build(int l, int r, int f) {
if(l > r) return 0;
int mid = (l + r) / 2;
int x = newnode(mid, f);
ch[x][0] = build(l, mid - 1, x);
ch[x][1] = build(mid + 1, r, x);
pushup(x);
return x;
}
inline void init(int x) {root = tot = 0; root = build(0, x + 1, 0);}
inline void cut(int l, int r, int c) {
splay(get_kth(root, l), 0); splay(get_kth(root, r + 2), root);
int tmp = ch[ch[root][1]][0];
ch[ch[root][1]][0] = 0;
pushup(ch[root][1]); pushup(root);
splay(get_kth(root, c + 1), 0); splay(get_kth(root, c + 2), root);
fa[tmp] = ch[root][1];
ch[ch[root][1]][0] = tmp;
pushup(ch[root][1]); pushup(root);
}
inline void filp(int l, int r) {
splay(get_kth(root, l), 0); splay(get_kth(root, r + 2), root);
lazy[ch[ch[root][1]][0]] ^= 1;
pushup(ch[root][1]); pushup(root);
}
int n, m, a, b, c;
int cnt;
void out(int x){
if (!x) return;
pushdown(x);
out(ch[x][0]);
if (key[x] >= 1 && key[x] <= n) {
cnt++;
printf("%d", key[x]);
if (cnt < n) printf(" ");
else puts("");
}
out(ch[x][1]);
}
char opt[20];
int main() {
while(scanf("%d%d", &n, &m) != EOF) {
if(n == -1 && m == -1) break;
init(n);
for(int i = 1; i <= m ;++i) {
scanf("%s", opt);
if(opt[0] == 'C') {
scanf("%d%d%d", &a, &b, &c); cut(a, b, c);
}else scanf("%d%d", &a, &b, &c), filp(a, b);
}
cnt = 0; out(root);
}
return 0;
}

【HDU 3487】Play with Chain Splay的更多相关文章

  1. Play with Chain 【HDU - 3487】【Splay+TLE讲解】

    题目链接 很好的一道题,用了三天多的时间,终于知道了我为什么T的原因,也知道了在Splay的同时该怎样子的节约时间,因为Splay本身就是大常数的O(N*logN),我们如果不在各种细节上节约时间,很 ...

  2. 【数位dp】【HDU 3555】【HDU 2089】数位DP入门题

    [HDU  3555]原题直通车: 代码: // 31MS 900K 909 B G++ #include<iostream> #include<cstdio> #includ ...

  3. 【HDU 5647】DZY Loves Connecting(树DP)

    pid=5647">[HDU 5647]DZY Loves Connecting(树DP) DZY Loves Connecting Time Limit: 4000/2000 MS ...

  4. -【线性基】【BZOJ 2460】【BZOJ 2115】【HDU 3949】

    [把三道我做过的线性基题目放在一起总结一下,代码都挺简单,主要就是贪心思想和异或的高斯消元] [然后把网上的讲解归纳一下] 1.线性基: 若干数的线性基是一组数a1,a2,a3...an,其中ax的最 ...

  5. 【HDU 2196】 Computer(树的直径)

    [HDU 2196] Computer(树的直径) 题链http://acm.hdu.edu.cn/showproblem.php?pid=2196 这题可以用树形DP解决,自然也可以用最直观的方法解 ...

  6. 【HDU 2196】 Computer (树形DP)

    [HDU 2196] Computer 题链http://acm.hdu.edu.cn/showproblem.php?pid=2196 刘汝佳<算法竞赛入门经典>P282页留下了这个问题 ...

  7. 【HDU 5145】 NPY and girls(组合+莫队)

    pid=5145">[HDU 5145] NPY and girls(组合+莫队) NPY and girls Time Limit: 8000/4000 MS (Java/Other ...

  8. 【hdu 1890】Robotic Sort

    [题目链接]:http://acm.hdu.edu.cn/showproblem.php?pid=1890 [题意] 给你n个数字; i从1到n; 每次让你把第i小的数和数组的第i个元素之间这段区间内 ...

  9. 【bzoj1552/3506】[Cerc2007]robotic sort splay翻转,区间最值

    [bzoj1552/3506][Cerc2007]robotic sort Description Input 输入共两行,第一行为一个整数N,N表示物品的个数,1<=N<=100000. ...

随机推荐

  1. 高速掌握Lua 5.3 —— Lua与C之间的交互概览

    Q:什么是Lua的虚拟栈? A:C与Lua之间通信关键内容在于一个虚拟的栈.差点儿全部的调用都是对栈上的值进行操作,全部C与Lua之间的数据交换也都通过这个栈来完毕.另外,你也能够使用栈来保存暂时变量 ...

  2. Atitit.ati&#160;dwr的原理and设计&#160;attilax&#160;总结&#160;java&#160;php&#160;版本号

    Atitit.ati dwr的原理and设计 attilax 总结 java php 版本号 1. dwr的长处相对于ajax来说.. 1 2. DWR工作原理 1 3. Dwr的架构 2 4. 自己 ...

  3. ngui 输入事件处理

    NGUI不仅提供了图形接口,还提供了输入事件接口!事件接口是通过UICamera来实现的. Unity3d 为我们提供的原装的input尽管非常方便,但真正跨平台使用时(尤其是跨手机与Pc机时)仍然不 ...

  4. Oracle 11g新增not null的字段比10g快--新特性

    在11g之前添加一个not null的字段很慢.在11g之后就很快了.我们先做一个測试,然后探究下原理. SQL> select * from v$version; BANNER ------- ...

  5. 企业级API设计

    最近对service的API设计,在team内有些讨论,主要集中在API是足够抽象.通用好呢, 还是具体.易用好? 其实这个是要折衷的,通用的好处是以后更改API的可能性小,但坏处是想要通用,里面的字 ...

  6. jQuery Validate(二)

    刚刚试了所谓的新版的用法.千万别问我是多新,因为我也不知道... <!DOCTYPE html> <html> <head> <script src=&quo ...

  7. 基于Python的安卓图形锁破解程序

    安卓手机的图形锁是3x3的点阵,按次序连接数个点从而达到锁定/解锁的功能.最少需要连接4个点,最多能连接9个点.网上也有暴力删除手机图形锁的方法,即直接干掉图形锁功能.但假如你想进入别人的手机,但又不 ...

  8. Window下安装Gradle并在IDEA中配置

    真是作死啊,Maven都只是用得半瓢水,还来搞Gradle,小心撩得一身骚啊. 下载Gradle 下载页面为:https://gradle.org/releases/ Gradle 4.1的下载地址: ...

  9. Linux的经常使用命令(1) - 指定执行级别

    命令:init [0123456] 执行级别 0:关机 1:单用户 2:多用户状态没有网络服务 3:多用户状态有网络服务 4:系统未使用保留给用户 5:图形界面 6:系统重新启动 经常使用执行级别是3 ...

  10. process_thread_action

    import psycopg2 import threading conn_fmac = psycopg2.connect(database='filter_useless_mac', user='u ...