BZOJ3506/1502 [CQOI2014]排序机械臂
依然是一道splay的区间操作,需要注意的是要把下标离散化后来表示splay的节点,我不知道怎么搞所以索性弄了个$ValuetoNode$,看样子没什么问题,
感觉他那个传下标的方法太暴力了..应该可以优化
//BZOJ 1552
//by Cydiater
//2016.9.7
#include <iostream>
#include <cstdio>
#include <cstring>
#include <string>
#include <algorithm>
#include <queue>
#include <map>
#include <ctime>
#include <cmath>
#include <iomanip>
#include <cstdlib>
using namespace std;
#define ll long long
#define up(i,j,n) for(int i=j;i<=n;i++)
#define down(i,j,n) for(int i=j;i>=n;i--)
;
const int oo=0x3f3f3f3f;
inline int read(){
,f=;
;ch=getchar();}
+ch-';ch=getchar();}
return x*f;
}
,root=,tol=,ValuetoNode[MAXN],q[MAXN],head,tail;
struct _data{
int id,v;
}a[MAXN];
struct SplayTree{
],fa,siz,v,tag;
}t[MAXN];
namespace solution{
inline ]==node;}
inline bool cmp(_data x,_data y){return x.v==y.v?x.id<y.id:x.v<y.v;}
inline bool re_cmp(_data x,_data y){return x.id<y.id;}
void updata(int node){
if(node){
t[node].siz=;
])t[node].siz+=t[t[node].son[]].siz;
])t[node].siz+=t[t[node].son[]].siz;
}
}
void downit(int node){
if(t[node].tag){
],rightson=t[node].son[];
;;
swap(t[node].son[],t[node].son[]);
t[node].tag=;
}
}
void rotate(int node){
int old=t[node].fa,oldf=t[old].fa,which=get(node);
t[old].son[which]=t[node].son[which^];t[t[old].son[which]].fa=old;
t[old].fa=node;t[node].son[which^]=old;t[node].fa=oldf;
]]=node;
updata(old);updata(node);
}
void build(int leftt,int rightt,int node,int fa){
if(leftt==rightt){
t[node].v=a[leftt].v;t[node].fa=fa;t[node].son[]=t[node].son[]=;
t[node].siz=;ValuetoNode[a[leftt].v]=node;t[node].tag=;
return;
}
t[node].tag=;
t[node].fa=fa;;
t[node].v=a[mid].v;ValuetoNode[a[mid].v]=node;
>=leftt){
t[node].son[]=++tol;build(leftt,mid-,tol,node);
}
<=rightt){
t[node].son[]=++tol;build(mid+,rightt,tol,node);
}
updata(node);
}
void splay(int node,int aim){
for(int fa;(fa=t[node].fa);rotate(node)){
if(node==aim)break;
if(t[node].fa==aim){
rotate(node);
break;
}
if(t[fa].fa==aim){
rotate(get(node)==get(fa)?fa:node);
rotate(node);
break;
}
if(t[fa].fa!=aim)rotate(get(node)==get(fa)?fa:node);
}
if(aim==root)root=node;
}
int find(int num){
int now=root;
){
downit(now);
]?t[t[now].son[]].siz:);
];
else{
)return now;
num-=(tmp+);
now=t[now].son[];
}
}
}
void init(){
N=read();
a[].v=oo;a[].id=;
up(i,,N+){
a[i].v=read();
a[i].id=i;
}N++;
a[++N].v=oo;a[N].id=N;
sort(a+,a+N+,cmp);
up(i,,N)a[i].v=++cnt;//sort by value
root=++tol;
sort(a+,a+N+,re_cmp);
build(,N,root,);
}
void slove(){
up(i,,N-){
int node=ValuetoNode[i];
head=;tail=;q[++tail]=node;;
int tmp=t[node].fa;
while(tmp!=root){
q[++tail]=tmp;
tmp=t[tmp].fa;
}q[++tail]=root;
while(head<=tail){
tmp=q[tail--];
downit(tmp);
}
splay(node,root);right_siz=t[t[root].son[]].siz+;
printf();)printf(" ");
int leftt=find(i),rightt=find(right_siz);
splay(leftt,root);splay(rightt,t[root].son[]);
];
t[Son].tag^=;
}
puts("");
}
}
int main(){
//freopen("input.in","r",stdin);
using namespace solution;
init();
slove();
;
}
BZOJ3506/1502 [CQOI2014]排序机械臂的更多相关文章
- 【BZOJ3506】[CQOI2014] 排序机械臂(Splay)
点此看题面 大致题意: 给你\(n\)个数.第一次找到最小值所在位置\(P_1\),翻转\([1,P_1]\),第二次找到剩余数中最小值所在位置\(P_2\),翻转\([2,P_2]\),以此类推.求 ...
- P3165 [CQOI2014]排序机械臂
题目描述 为了把工厂中高低不等的物品按从低到高排好序,工程师发明了一种排序机械臂.它遵循一个简单的排序规则,第一次操作找到高度最低的物品的位置 P1P_1P1 ,并把左起第一个物品至 P1P_1P1 ...
- 洛谷P3165 [CQOI2014]排序机械臂
题目描述 为了把工厂中高低不等的物品按从低到高排好序,工程师发明了一种排序机械臂.它遵循一个简单的排序规则,第一次操作找到摄低的物品的位置P1,并把左起第一个至P1间的物品反序:第二次找到第二低的物品 ...
- bzoj3506 [Cqoi2014]排序机械臂
bzoj3506 此题是一道比较简单的spaly题目. 用splay维护序列,将每个点排到对应的位置之后删除,这样比较容易区间翻转. 我的指针写法在洛谷上AC了,但在bzoj上RE. #include ...
- BZOJ1552[Cerc2007]robotic sort&BZOJ3506[Cqoi2014]排序机械臂——非旋转treap
题目描述 输入 输入共两行,第一行为一个整数N,N表示物品的个数,1<=N<=100000. 第二行为N个用空格隔开的正整数,表示N个物品最初排列的编号. 输出 输出共一行,N个用空格隔开 ...
- [BZOJ3506] [Cqoi2014] 排序机械臂 (splay)
Description 同OJ1552 Input Output Sample Input Sample Output HINT Source Solution Q:哎不是同一道题吗为什么分两篇博客来 ...
- [bzoj1552][Cerc2007]robotic sort&&[bzoj3506][Cqoi2014]排序机械臂
非常垃圾的一道平衡树,结果被日了一天.很难受嗷嗷嗷 首先不得不说网上的题解让我这个本来就不熟悉平衡树的彩笔很难受——并不好理解. 还好Sinogi大佬非常的神,一眼就切掉了,而且用更加美妙的解法. 题 ...
- Luogu P3165 [CQOI2014]排序机械臂
先讲一下和这题一起四倍经验的题: Luogu P4402 [Cerc2007]robotic sort 机械排序 SP2059 CERC07S - Robotic Sort UVA1402 Robot ...
- 【洛谷 P3165】 [CQOI2014]排序机械臂 (Splay)
题目链接 debug了\(N\)天没debug出来,原来是找后继的时候没有pushdown... 众所周知,,Splay中每个编号对应的节点的值是永远不会变的,因为所有旋转.翻转操作改变的都是父节点和 ...
随机推荐
- STL中的next_permutation
给定一个数组a[N],求下一个数组. 2 1 3 4 2 1 4 3 2 3 1 4 2 3 4 1 ..... 在STL中就有这个函数: 1.参数是(数组的第一个元素,数组的末尾),注意这是前闭后开 ...
- Openstack Basic Networking 翻译
自己翻译,加强理解.并学习英文和写作. 英文地址:http://docs.openstack.org/networking-guide/intro_basic_networking.html 目录: ...
- 网络流最小割 POJ 3469
题意 2个CPU n个任务 给出在第一个 第二个运行时的花费 m 个 a b 不在同一个CPU运行的额外花费 建图 源点 -> n -> 汇点 权 a1 ...
- 将现有的sql脚本导入 Oracle 数据库,中文乱码问题
将现有的sql 脚本导入 Oracle数据库 比如 在windows 系统下,可以写一个 bat 来实现直接导入 如:bat 中的内容如下,logs.log 将会记录执行日志 sqlplus user ...
- windows系统激活-使用微软官方公布的kms client setup key安装或安装后使用slmgr导入
windows 10各版本: Windows 10 Professional W269N-WFGWX-YVC9B-4J6C9-T83GX Windows 10 Professional N MH37W ...
- 数据库开发基础-SQl Server 聚合函数、数学函数、字符串函数、时间日期函数
SQL 拥有很多可用于计数和计算的内建函数. 函数的语法 内建 SQL 函数的语法是: SELECT function(列) FROM 表 函数的类型 在 SQL 中,基本的函数类型和种类有若干种.函 ...
- C++11特性:auto关键字
前言 本文的内容已经不新鲜了.关于auto,翻来覆去被人知道的都是这些东西,本文并没有提出新颖的auto用法. 本人原是痛恨博客一篇篇都是copy而来缺乏新意的探索,当然,本文不是copy而来,但发布 ...
- 【unity shaders】:Unity中的Shader及其基本框架
shader和Material的基本关系 Shader(着色器)实际上就是一小段程序,它负责将输入的Mesh(网格)以指定的方式和输入的贴图或者颜色等组合作用,然后输出.绘图单元可以依据这个输出来将图 ...
- 利用Quartz2D推图的另一个方法 (使用CGMutalePathRef进行分层次)
可以利用 CGMutablePathRef 创建每个不同图形,然后再一起添加到CGContext中 - (void)drawRect:(CGRect)rect { CGContextRef ctx = ...
- C++之再续前缘(一)——C++基础(与C语言的差异)(下)
1.void型指针 void本身是一种数据类型,通常表示无值,不能声明void类型的变量,但是可以声明void类型的指针, void*类型的指针表示不确定的类型,是一种通用型的指针,也就是说任何类型的 ...