HDU 1754 I Hate It

来源:互联网 发布:智能手环 数据接口 编辑:程序博客网 时间:2024/05/17 04:09

水题,Splay做下。建树时直接根据id顺序建树,首尾增加两个节点。询问操作先见l-1旋转至根节点,再将r+1旋转至l-1右节点处。旋转后[l,r]节点都在r+1左子树上。r+1左儿子res值即为所求值。

#include <cstdio>#include <iostream>#include <algorithm>#include <cstring>using namespace std;#define N 200005#define mod 20140518const int inf = (1 << 29);typedef long long LL;int n, m;int pre[N], key[N], ch[N][2], root, tot1, res[N];int cnt[N];//ch[][0]为左孩子,ch[][1]为右孩子void NewNode(int r, int val){    ch[r][0] = ch[r][1] = 0;    pre[r] = r - 1;    res[r] = key[r] = val;    ch[r - 1][1] = r;}void pushup(int x){    res[x] = max(res[ch[x][0]], res[ch[x][1]]);    res[x] = max(res[x], key[x]);}//kind = 1为右旋,kind为0左旋void Rotate(int x,int kind){    int y = pre[x];    ch[y][!kind] = ch[x][kind];    pre[ch[x][kind]] = y;    if(pre[y]){        ch[pre[y]][ch[pre[y]][1] == y] = x;    }//y节点有父节点用x节点将其替代    pre[x] = pre[y];    ch[x][kind] = y;    pre[y] = x;    pushup(y);}void Splay(int r, int goal){    while(pre[r] != goal){        int y = pre[r];        int kind = (ch[y][0] == r);        if(pre[y] != goal && (kind == (ch[pre[y]][0] == y))){            Rotate(y, kind);        }        Rotate(r, kind);    }    pushup(r);    if(goal == 0)root = r;}void update(int r, int val){    Splay(r, 0);    key[r] = val;    pushup(r);}int Query(int l, int r){    Splay(l - 1, 0);    Splay(r + 1, l - 1);    return res[ch[r + 1][0]];}int main(){    while(scanf("%d%d", &n, &m) != EOF){        NewNode(1, -inf);        int q, v;        for(int i = 1; i <= n; i++){            scanf("%d", &v);            NewNode(i + 1, v);        }        NewNode(n + 2, -inf);        for(int i = n + 2; i; i--){            pushup(i);        }        root = 1;        char c[10];        for(int i = 0; i < m; i++){            scanf("%s%d%d", c, &q, &v);            if(c[0] == 'Q')                printf("%d\n", Query(q + 1, v + 1));            else update(q + 1, v);        }    }    return 0;}


0 0
原创粉丝点击