【双Treap】[Scoi2014] bzoj3595 方伯伯的Oj

来源:互联网 发布:一个二次元软件 有后山 编辑:程序博客网 时间:2024/05/16 15:35

题目点这里 原来的题解点这里 。。Treap+Map写的。。。


。。然后听说scoi的评测鸡很傲娇。。。。当场是卡了map的。。。。

所以我就重新写了双Treap。。。一个维护编号一个维护排名。。。。。。


叫bzoj比map慢了几十ms = =因为有-O2?

rank3是的评测结果 rank4和rank5目测都是直接交的我的代码吧 = =||||

然后rank6就是这份代码的评测结果了。。。


回绵阳了以后用cena测测试试。。。按理说手写应该还是能比STL快的?

(ac代码有问题 仅供参考!!)

#include <cstdio>#include <iostream>#include <cstdlib>using namespace std;int read(){int n = 0, sign = 1; char c = getchar();while(c > '9' || c < '0') {if(c == '-') sign = -1; c = getchar();}while(c >= '0' && c <= '9') {n = n*10 + c-'0'; c = getchar(); }return sign * n;}const int inf = 0x3f3f3f3f;int cnt = 1, tot = 1;struct Treap{struct node{node *lc, *rc;int s, id, r, L, R;}t[300055], *null, *root;inline void init(){null = &t[0]; null -> lc = null -> rc = null;null -> s = 0; null -> id = null -> L = null -> R = null -> r = -inf;root = null;}inline node *NewNode(int index, int L, int R){t[cnt].lc = t[cnt].rc = null; t[cnt].r = rand();t[cnt].id = index; t[cnt].L = L; t[cnt].R = R; t[cnt].s = R - L + 1;return &t[cnt++];}inline void pushup(node *&p){ p->s = p->lc->s + p->rc->s + (p->R-p->L+1);}inline void maintain(node *&p){if(p->lc->r > p->r){node *temp = p -> lc;p -> lc = temp -> rc;temp -> rc = p;pushup(p); p = temp;} else if(p->rc->r > p->r){node *temp = p -> rc;p -> rc = temp -> lc;temp -> lc = p;pushup(p); p = temp;}pushup(p);}void insert(node *&p, int L, int R, int index){if(p == null){p = NewNode(index, L, R);return;}if(R < p -> L) insert(p -> lc, L, R, index);else insert(p -> rc, L, R, index);maintain(p);}void merge(node *&ne, node *p, node *q){if(p == null || q == null){ne = p == null ? q : p;return;}if(p->r > q->r) { ne = p; merge(ne->rc, p->rc, q); }else{ ne = q; merge(ne->lc, p, q->lc); }pushup(ne);}void del(node *&p, int pos){if(p == null) return;if(p->L <= pos && pos <= p->R){if(p->L == p->R) merge(p, p->lc, p->rc);else if(p->L == pos) { ++ p -> L; ++ p -> id; pushup(p); }else if(p->R == pos) { -- p -> R; pushup(p); }else{insert(p -> rc, pos + 1, p -> R, pos + 1);p -> R = pos - 1; pushup(p);}return;}if(p->L > pos) del(p -> lc, pos);else del(p -> rc, pos); maintain(p);}int getrank(node *p, int pos){if(p == null) return 0;if(p->L <= pos && pos <= p->R) return (pos - p->L + 1) + p->lc->s;if(p->L > pos) return getrank(p->lc, pos);else return getrank(p->rc, pos) + p->lc->s + (p->R - p->L + 1);}int getindex(node *p, int k){if(p == null) return 0;int lsize = p->lc->s; if(k <= lsize) return getindex(p->lc, k);if(lsize < k && lsize + (p->R - p->L + 1) >= k){if(p->L == p->R) return p->id;else return k-lsize-1 + p->L;}else return getindex(p->rc, k - lsize - (p->R - p->L + 1));}}t;struct Map{struct node{node *lc, *rc;int r, id, rank;}t[300055], *null, *root;inline void init(){null = &t[0]; null -> lc = null -> rc = null;null -> rank = null -> r = -inf; root = null;}inline node *NewNode(int index, int rank){t[tot].lc = t[tot].rc = null; t[tot].r = rand();t[tot].id = index; t[tot].rank = rank; return &t[tot++];}inline void maintain(node *&p){if(p->lc->r > p->r){node *temp = p -> lc;p -> lc = temp -> rc;temp -> rc = p; p = temp;} else if(p->rc->r > p->r){node *temp = p -> rc;p -> rc = temp -> lc;temp -> lc = p; p = temp;}}void insert(node *&p, int index, int rank){if(p == null){p = NewNode(index, rank);return;}if(index == p -> id) p -> rank = rank;else if(index < p -> id) insert(p -> lc, index, rank);else insert(p -> rc, index, rank);maintain(p);}int find(node *p, int index){if(p == null) return 0;if(p -> id == index) return p -> rank; if(p -> id > index) return find(p -> lc, index);return find(p -> rc, index);}void remove(node *p, int index){if(p == null) return;if(p -> id == index) p -> rank = 0;else if(p -> id > index) remove(p -> lc, index);else remove(p -> rc, index);}}m; int N, M;int main(){srand(20150233); t.init(); m.init();N = read(); t.insert(t.root, 1, N, 1);int mmin = 0, mmax = N, a = 0; for(M = read(); M--; ){int sign = read(), x = read(); x -= a;if(sign == 1){int y = read(); y -= a;int pos = m.find(m.root, x); if(!pos) pos = x;printf("%d\n", a = t.getrank(t.root, pos));t.del(t.root, pos); t.insert(t.root, pos, pos, y); m.remove(m.root, x); m.insert(m.root, y, pos);}else if(sign == 2){int pos = m.find(m.root, x); if(!pos) pos = x;printf("%d\n", a = t.getrank(t.root, pos));t.del(t.root, pos); m.insert(m.root, x, pos = --mmin); t.insert(t.root, pos, pos, x);}else if(sign == 3){int pos = m.find(m.root, x); if(!pos) pos = x;printf("%d\n", a = t.getrank(t.root, pos));t.del(t.root, pos); m.insert(m.root, x, pos = ++mmax); t.insert(t.root, pos, pos, x);}else printf("%d\n", a = t.getindex(t.root, x));}return 0;}


0 0
原创粉丝点击