Play with Chain

Time Limit: 6000/2000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)
Total Submission(s): 2783    Accepted Submission(s): 1141

Problem Description
YaoYao is fond of playing his chains. He has a chain containing n diamonds on it. Diamonds are numbered from 1 to n.
At first, the diamonds on the chain is a sequence: 1, 2, 3, …, n.
He will perform two types of operations:
CUT a b c: He will first cut down the chain from the ath diamond to the bth diamond. And then insert it after the cth diamond on the remaining chain.
For example, if n=8, the chain is: 1 2 3 4 5 6 7 8; We perform “CUT 3 5 4”, Then we first cut down 3 4 5, and the remaining chain would be: 1 2 6 7 8. Then we insert “3 4 5” into the chain before 5th diamond, the chain turns out to be: 1 2 6 7 3 4 5 8.

FLIP a b: We first cut down the chain from the ath diamond to the bth diamond. Then reverse the chain and put them back to the original position.
For example, if we perform “FLIP 2 6” on the chain: 1 2 6 7 3 4 5 8. The chain will turn out to be: 1 4 3 7 6 2 5 8

He wants to know what the chain looks like after perform m operations. Could you help him?

 
Input
There will be multiple test cases in a test data. 
For each test case, the first line contains two numbers: n and m (1≤n, m≤3*100000), indicating the total number of diamonds on the chain and the number of operations respectively.
Then m lines follow, each line contains one operation. The command is like this:
CUT a b c // Means a CUT operation, 1 ≤ a ≤ b ≤ n, 0≤ c ≤ n-(b-a+1).
FLIP a b    // Means a FLIP operation, 1 ≤ a < b ≤ n.
The input ends up with two negative numbers, which should not be processed as a case.
 
Output
For each test case, you should print a line with n numbers. The ith number is the number of the ith diamond on the chain.
 
Sample Input
8 2
CUT 3 5 4
FLIP 2 6
-1 -1
 
Sample Output
1 4 3 7 6 2 5 8
 
Source
 
Recommend
zhengfeng
 /* ***********************************************
Author :kuangbin
Created Time :2013/8/25 23:35:30
File Name :F:\2013ACM练习\专题学习\splay_tree_2\HDU3487.cpp
************************************************ */ #include <stdio.h>
#include <string.h>
#include <iostream>
#include <algorithm>
#include <vector>
#include <queue>
#include <set>
#include <map>
#include <string>
#include <math.h>
#include <stdlib.h>
#include <time.h>
using namespace std; #define Key_value ch[ch[root][1]][0]
const int MAXN = ;
int pre[MAXN],ch[MAXN][],root,tot1;
int key[MAXN],rev[MAXN];
int size[MAXN];
int s[MAXN],tot2;
int n,q; void NewNode(int &r,int father,int k)
{
if(tot2) r = s[tot2--];
else r = ++tot1;
key[r] = k;
pre[r] = father;
rev[r] = ;
ch[r][] = ch[r][] = ;
size[r] = ;
}
//反转的更新
void Update_Rev(int r)
{
if(!r) return;
swap(ch[r][],ch[r][]);
rev[r] ^= ;
}
void push_up(int r)
{
size[r] = size[ch[r][]] + size[ch[r][]] + ;
}
void push_down(int r)
{
if(rev[r])
{
Update_Rev(ch[r][]);
Update_Rev(ch[r][]);
rev[r] = ;
}
} void Build(int &x,int l,int r,int father)
{
if(l > r)return;
int mid = (l+r)/;
NewNode(x,father,mid);
Build(ch[x][],l,mid-,x);
Build(ch[x][],mid+,r,x);
push_up(x);
}
void Init()
{
root = tot1 = tot2 = ;
ch[root][] = ch[root][] = size[root] = key[root] = pre[root] = rev[root] = ;
NewNode(root,,-);
NewNode(ch[root][],root,-);
Build(Key_value,,n,ch[root][]);
push_up(ch[root][]);
push_up(root);
}
void Rotate(int x,int kind)
{
int y = pre[x];
push_down(y);
push_down(x);
ch[y][!kind] = ch[x][kind];
pre[ch[x][kind]] = y;
if(pre[y])
ch[pre[y]][ch[pre[y]][]==y] = x;
pre[x] = pre[y];
ch[x][kind] = y;
pre[y] = x;
push_up(y);
}
void Splay(int r,int goal)
{
push_down(r);
while(pre[r] != goal)
{
if(pre[pre[r]] == goal)
{
push_down(pre[r]);
push_down(r);
Rotate(r,ch[pre[r]][]==r);
}
else
{
push_down(pre[pre[r]]);
push_down(pre[r]);
push_down(r);
int y = pre[r];
int kind = ch[pre[y]][]==y;
if(ch[y][kind] == r)
{
Rotate(r,!kind);
Rotate(r,kind);
}
else
{
Rotate(y,kind);
Rotate(r,kind);
}
}
}
push_up(r);
if(goal == )root = r;
}
int Get_kth(int r,int k)
{
push_down(r);
int t = size[ch[r][]] + ;
if(t == k)return r;
if(t > k)return Get_kth(ch[r][],k);
else return Get_kth(ch[r][],k-t);
}
//将[l,r]段剪切下来,放在剩下段的第c个后面
void CUT(int l,int r,int c)
{
Splay(Get_kth(root,l),);
Splay(Get_kth(root,r+),root);
int tmp = Key_value;
Key_value = ;
push_up(ch[root][]);
push_up(root);
Splay(Get_kth(root,c+),);
Splay(Get_kth(root,c+),root);
Key_value = tmp;
pre[Key_value] = ch[root][];
push_up(ch[root][]);
push_up(root);
}
//将[l,r]段反转
void FLIP(int l,int r)
{
Splay(Get_kth(root,l),);
Splay(Get_kth(root,r+),root);
Update_Rev(Key_value);
push_up(ch[root][]);
push_up(root);
}
//按顺序输出
int cnt;
void InOrder(int r)
{
if(!r)return;
push_down(r);
InOrder(ch[r][]);
if(cnt >= && cnt <= n)
{
printf("%d",key[r]);
if(cnt < n)printf(" ");
else printf("\n");
}
cnt++;
InOrder(ch[r][]);
}
int main()
{
//freopen("in.txt","r",stdin);
//freopen("out.txt","w",stdout);
while(scanf("%d%d",&n,&q) == )
{
if( n < && q < )break;
Init();
char op[];
int x,y,z;
while(q--)
{
scanf("%s",op);
if(op[] == 'C')
{
scanf("%d%d%d",&x,&y,&z);
CUT(x,y,z);
}
else
{
scanf("%d%d",&x,&y);
FLIP(x,y);
}
}
cnt = ;
InOrder(root);
}
return ;
}

HDU 3487 Play with Chain (splay tree)的更多相关文章

  1. HDU 3487 Play with Chain(Splay)

    题目大意 给一个数列,初始时为 1, 2, 3, ..., n,现在有两种共 m 个操作 操作1. CUT a b c 表示把数列中第 a 个到第 b 个从原数列中删除得到一个新数列,并将它添加到新数 ...

  2. HDU 3487 Play with Chain 【Splay】

    1-n的序列,有两种操作: 1,将一段区间翻转 2,将一段区间切下来放到剩余序列的第C个数后 采用延迟更新的方法维护区间的翻转,并维护一个size域. 添加一个最大点和一个最小点,防止出界 翻转时,将 ...

  3. HDU 3478 Play with Chain (Splay树)

    这种高级数据结构太难搞了.........现在还是先照着别人的代码敲,做模板..........慢慢花时间来弄懂 #include <iostream> #include <algo ...

  4. 伸展树(Splay Tree)进阶 - 从原理到实现

    目录 1 简介 2 基础操作 2.1 旋转 2.2 伸展操作 3 常规操作 3.1 插入操作 3.2 删除操作 3.3 查找操作 3.4 查找某数的排名.查找某排名的数 3.4.1 查找某数的排名 3 ...

  5. 数据结构(二) --- 伸展树(Splay Tree)

    文章图片和代码来自邓俊辉老师课件 概述 伸展树(Splay Tree),也叫分裂树,是一种二叉排序树,它能在O(log n)内完成插入.查找和删除操作.它由丹尼尔·斯立特Daniel Sleator ...

  6. HDU 1890 Robotic Sort (splay tree)

    Robotic Sort Time Limit: 6000/2000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Tota ...

  7. hdu 3487 Play with Chain

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3487 YaoYao is fond of playing his chains. He has a c ...

  8. 纸上谈兵:伸展树(splay tree)

    作者:Vamei 出处:http://www.cnblogs.com/vamei 欢迎转载,也请保留这段声明.谢谢! 我们讨论过,树的搜索效率与树的深度有关.二叉搜索树的深度可能为n,这种情况下,每次 ...

  9. bzoj1251 序列终结者(Splay Tree+懒惰标记)

    Description 网上有许多题,就是给定一个序列,要你支持几种操作:A.B.C.D.一看另一道题,又是一个序列 要支持几种操作:D.C.B.A.尤其是我们这里的某人,出模拟试题,居然还出了一道这 ...

随机推荐

  1. TF-tf.nn.dropout介绍

    官方的接口是这样的 tf.nn.dropout(x, keep_prob, noise_shape=None, seed=None, name=None) 根据给出的keep_prob参数,将输入te ...

  2. QUnit 实践一

    项目准备启用Qunit, 先来尝试一下. 不说废话,上代码: <!DOCTYPE HTML> <html> <head> <meta http-equiv=& ...

  3. 1.SpringBoot之Helloword 快速搭建一个web项目

    背景: Spring Boot是由Pivotal团队提供的全新框架,其设计目的是用来简化新Spring应用的初始搭建以及开发过程.该框架使用了特定的方式来进行配置,从而使开发人员不再需要定义样板化的配 ...

  4. Python基础 - eazy_install和pip源设置

    在国内一般推荐豆瓣的源,虽然工作中用到的都是公司内部的源,出于安全考虑这里就不拿公司的源举例了~ 1. pip源设置 打开~/.pip/pip.conf文件,若文件不存在则创建文件或者直接mkdir ...

  5. java IO流之——File类知识总结和面试

    File类描述的是一个文件或文件夹.(文件夹也可以称为目录).该类的出现是对文件系统的中的文件以及文件夹进行对象的封装.可以通过对象的思想来操作文件以及文件夹.可以用面向对象的处理问题,通过该对象的方 ...

  6. HDU 2476 String painter(区间DP+思维)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2476 题目大意:给你字符串A.B,每次操作可以将一段区间刷成任意字符,问最少需要几次操作可以使得字符串 ...

  7. 使用django发送邮件时的连接超时问题解决

    一.报错 研究报错半天,没看出代码有什么毛病,就是发送邮件时连接超时,发送邮件的连接用户名密码都没有错误,于是就网上各种查... 终于皇天不负有心人,找到答案了.. 在服务器上输入telnet smt ...

  8. ubuntu16.04 安装 caffe cuda 相关流程

    不多说了,经历了很多莫名其妙的错误最后终于安装好了,直接放安装脚本: #!/bin/bash #安装时要注意有些库可能安装失败以及安装caffe有和protobuf相关错误时可能需要重新对protob ...

  9. Linux下的堆off-by-one的利用

    这篇稿子已经投到了360安全播报,http://bobao.360.cn/learning/detail/3113.html

  10. IdentityServer4揭秘---登录

    IdentityServer4默认提供了的登录地址是Account/Index 同意页面是Consent/Index 这里我们可以通过IdentittyServer4的用户交互自定义配置设置 在Con ...