• P3165 [CQOI2014]排序机械臂


    P3165 [CQOI2014]排序机械臂

    题目描述

    为了把工厂中高低不等的物品按从低到高排好序,工程师发明了一种排序机械臂。它遵循一个简单的排序规则,第一次操作找到摄低的物品的位置P1,并把左起第一个至P1间的物品反序;第二次找到第二低的物品的位置P2,并把左起第二个至P2间的物品反序...最终所有的物品都会被排好序。

    上图给出_个示例,第_次操作前,菝低的物品在位置4,于是把第1至4的物品反序;第二次操作前,第二低的物品在位罝6,于是把第2至6的物品反序...

    你的任务便是编写一个程序,确定一个操作序列,即每次操作前第i低的物品所在位置Pi,以便机械臂工作。需要注意的是,如果有高度相同的物品,必须保证排序后它们的相对位置关系与初始时相同。

    输入输出格式

    输入格式:

    第一行包含正整数n,表示需要排序的物品数星。

    第二行包含n个空格分隔的整数ai,表示每个物品的高度。

    输出格式:

    输出一行包含n个空格分隔的整数Pi。

    输入输出样例

    输入样例#1: 复制
    6
    3 4 5 1 6 2
    输出样例#1: 复制
    4 6 4 5 6 6

    code

    神奇的splay

      1 #include<cstdio>
      2 #include<algorithm>
      3 
      4 using namespace std;
      5 
      6 const int N = 500100;
      7 const int INF = 1e9;
      8 
      9 int data[N],siz[N],mn[N],pos[N],tag[N],ch[N][2],fa[N],st[N];
     10 int Root,top;
     11 
     12 struct Data{
     13     int x,p;
     14 }d[N];
     15 
     16 inline char nc() {
     17     static char buf[100000],*p1 = buf,*p2 = buf;
     18     return p1==p2&&(p2=(p1=buf)+fread(buf,1,100000,stdin),p1==p2) ? EOF : *p1++;
     19 }
     20 inline int read() {
     21     int x = 0,f = 1;char ch = nc();
     22     for (; ch<'0'||ch>'9'; ch = nc())
     23         if (ch=='-') f = -1;
     24     for (; ch>='0'&&ch<='9'; ch = nc())
     25         x = x * 10 + ch - '0';
     26     return x * f;
     27 }
     28 bool cmp1(Data a,Data b) {
     29     if (a.x==b.x) return a.p < b.p;
     30     return a.x < b.x;
     31 }
     32 bool cmp2(Data a,Data b) {
     33     return a.p < b.p;
     34 }
     35 inline void pushup(int x) {
     36     int l = ch[x][0],r = ch[x][1];
     37     mn[x] = data[x],pos[x] = x;
     38     if (mn[l] < mn[x]) mn[x] = mn[l],pos[x] = pos[l];
     39     if (mn[r] < mn[x]) mn[x] = mn[r],pos[x] = pos[r];//-
     40     siz[x] = siz[l] + siz[r] + 1;
     41 }
     42 inline void pushdown(int x) {
     43     if (tag[x]) {
     44         tag[ch[x][0]] ^= 1;
     45         tag[ch[x][1]] ^= 1;
     46         swap(ch[x][0],ch[x][1]);
     47         tag[x] ^= 1;
     48     }
     49 }
     50 inline int son(int x) {
     51     return x == ch[fa[x]][1]; //-
     52 }
     53 inline void rotate(int x) {
     54     int y = fa[x],z = fa[y],b = son(x),c = son(y),a = ch[x][!b];
     55     if (z) ch[z][c] = x;else Root = x;fa[x] = z; //-
     56     ch[x][!b] = y;fa[y] = x;
     57     ch[y][b] = a;if (a) fa[a] = y;
     58     pushup(y);pushup(x);
     59 }
     60 inline void splay(int x,int rt) {
     61     top = 0;int p = x;//--
     62     while (p) st[++top] = p,p = fa[p];
     63     while (top) pushdown(st[top]),top--;
     64     while (fa[x] != rt) {
     65         int y = fa[x],z = fa[y];
     66         if (z==rt) rotate(x);
     67         else {
     68             if (son(x)==son(y)) rotate(y),rotate(x);
     69             else rotate(x),rotate(x);
     70         }
     71     }
     72 }
     73 inline int getkth(int k) {
     74     int p = Root;
     75     while (true) {
     76         pushdown(p);
     77         if (k == siz[ch[p][0]] + 1) return p;
     78         if (ch[p][0] && siz[ch[p][0]] >= k) p = ch[p][0];
     79         else {
     80             k -= ((ch[p][0] ? siz[ch[p][0]] : 0) + 1);
     81             p = ch[p][1];
     82         }
     83     }
     84 }
     85 inline int getmnpos(int l,int r) {
     86     int L = getkth(l),R = getkth(r+2);
     87     splay(L,0);
     88     splay(R,L);
     89     return pos[ch[R][0]];
     90 }
     91 inline void rever(int l,int r) {
     92     int L = getkth(l),R = getkth(r+2);
     93     splay(L,0);splay(R,L);
     94     tag[ch[R][0]] ^= 1;
     95 }
     96 int build(int l,int r) {
     97     if (l > r) return 0;
     98     /*if (l==r) {
     99         siz[l] = 1;data[l] = mn[l] = d[l].x;pos[l] = l;
    100         return l;
    101     }*/
    102     int mid = (l + r) >> 1;
    103     int t = build(l,mid-1);
    104     fa[t] = mid;ch[mid][0] = t;
    105     t = build(mid+1,r);
    106     fa[t] = mid;ch[mid][1] = t;
    107     data[mid] = d[mid].x; //= mn[mid]pos[mid] = mid;
    108     pushup(mid);
    109     return mid;
    110 }
    111 
    112 int main() {
    113     int n = read();
    114     d[1].x = d[n+2].x = mn[0] = INF;
    115     for (int i=2; i<=n+1; ++i) 
    116         d[i].x = read(),d[i].p = i;
    117     sort(d+2,d+n+2,cmp1);
    118     for (int i=2; i<=n+1; ++i) 
    119         d[i].x = i - 1; // 没有相等的 
    120     sort(d+2,d+n+2,cmp2);
    121     Root = build(1,n+2);
    122     for (int i=1; i<=n; ++i) {
    123         int x = getmnpos(i,n);
    124         splay(x,0);
    125         printf("%d ",siz[ch[x][0]]); // siz[ch[x][0]] + 1 - 1
    126         rever(i,siz[ch[x][0]]);
    127     }
    128     return 0;
    129 }
  • 相关阅读:
    Martix工作室考核题 —— 打印一个菱形
    Martix工作室考核题 —— 打印一个菱形
    Martix工作室考核题 —— 打印九九乘法表
    Martix工作室考核题 —— 打印九九乘法表
    Martix工作室考核题 —— 打印九九乘法表
    Martix工作室考核题 —— 201938 第三题
    Martix工作室考核题 —— 201938 第三题
    Martix工作室考核题 —— 201938 第三题
    Martix工作室考核题 —— 201938 第一题
    fiddler模拟发送post请求
  • 原文地址:https://www.cnblogs.com/mjtcn/p/8010619.html
Copyright © 2020-2023  润新知