• po3580SuperMemo(splay)


    链接

    操作不少,不过都是一些基本的操作,增删,旋转,逆转,询问最小。

    注意一点:T<0时 让t=0;

    旋转的时候,是顺时针旋转,数据范围在int内。

    刚开始旋转转错方向了。。

      1 #include <iostream>
      2 #include<cstdio>
      3 #include<cstring>
      4 #include<algorithm>
      5 #include<stdlib.h>
      6 #include<vector>
      7 #include<cmath>
      8 #include<queue>
      9 #include<set>
     10 using namespace std;
     11 #define N 200010
     12 #define LL long long
     13 #define INF 0xfffffff
     14 #define key_value ch[ch[root][1]][0]
     15 const double eps = 1e-8;
     16 const double pi = acos(-1.0);
     17 const double inf = ~0u>>2;
     18 using namespace std;
     19 int a[N];
     20 struct splay_tree
     21 {
     22     int pre[N],size[N];
     23     int ch[N][2];
     24     int root,tot;
     25     int lz2[N];
     26     LL s[N],lz1[N],key[N];
     27 //    void dfs(int x)
     28 //    {
     29 //        if(x)
     30 //        {
     31 //            dfs(ch[x][0]);
     32 //            printf("结点%2d:左儿子 %2d 右儿子 %2d 父结点 %2d size=%2d,key=%2d lz1 = %d lz2 = %d min = %d
    ",
     33 //                   x,ch[x][0],ch[x][1],pre[x],size[x],key[x],lz1[x],lz2[x],s[x]);
     34 //            dfs(ch[x][1]);
     35 //        }
     36 //    }
     37 //    void debug()
     38 //    {
     39 //        printf("root:%d
    ",root);
     40 //        dfs(root);
     41 //    }
     42 //以上用于debug*/
     43     void newnode(int &x,int v,int fa)//新建一结点
     44     {
     45         x = ++tot;
     46         ch[x][0]=ch[x][1] = 0;
     47         pre[x] = fa;
     48         lz1[x] = lz2[x] = 0;
     49         size[x] = 1;
     50         s[x] = v;
     51         key[x] = v;
     52     }
     53     void pushdown(int w)
     54     {
     55         int l = ch[w][0],r = ch[w][1];
     56         if(lz1[w])
     57         {
     58             lz1[l] += lz1[w];
     59             lz1[r] += lz1[w];
     60             s[l]+=lz1[w];
     61             s[r]+=lz1[w];
     62             key[l]+=lz1[w];
     63             key[r]+=lz1[w];
     64             lz1[w] = 0;
     65         }
     66         if(lz2[w])
     67         {
     68             lz2[l]^=lz2[w];
     69             lz2[r]^=lz2[w];
     70             swap(ch[w][0],ch[w][1]);
     71             lz2[w] = 0;
     72         }
     73     }
     74     void pushup(int w)
     75     {
     76         size[w] = size[ch[w][0]]+size[ch[w][1]]+1;
     77         s[w] = key[w];
     78         if(ch[w][0])
     79             s[w] = min(s[w],s[ch[w][0]]);
     80         if(ch[w][1])
     81             s[w] = min(s[w],s[ch[w][1]]);
     82     }
     83     void rotate(int r,int kind)
     84     {
     85         int y = pre[r];
     86         pushdown(y);
     87         pushdown(r);
     88         ch[y][!kind] = ch[r][kind];
     89         pre[ch[r][kind]] = y;
     90         if(pre[y])
     91         {
     92             ch[pre[y]][ch[pre[y]][1]==y] = r;
     93         }
     94         pre[r] = pre[y];
     95         ch[r][kind] = y;
     96         pre[y] = r;
     97         pushup(y);
     98         pushup(r);
     99     }
    100     void splay(int r,int goal)
    101     {
    102         pushdown(r);
    103         while(pre[r]!=goal)
    104         {
    105             if(pre[pre[r]]==goal)
    106             {
    107                 rotate(r,ch[pre[r]][0]==r);
    108             }
    109             else
    110             {
    111                 int y = pre[r];
    112                 int kind = (ch[pre[y]][0]==y);
    113                 if(ch[y][kind]==r)
    114                 {
    115                     rotate(r,!kind);
    116                     rotate(r,kind);
    117                 }
    118                 else
    119                 {
    120                     rotate(y,kind);
    121                     rotate(r,kind);
    122                 }
    123             }
    124         }
    125         pushup(r);
    126         if(goal==0) root = r;
    127     }
    128     int get_k(int k)
    129     {
    130         int r = root;
    131         pushdown(r);
    132         while(size[ch[r][0]]+1!=k)
    133         {
    134             if(size[ch[r][0]]>=k)
    135                 r = ch[r][0];
    136             else
    137             {
    138                 k-=(size[ch[r][0]]+1);
    139                 r = ch[r][1];
    140             }
    141             pushdown(r);
    142         }
    143         return r;
    144     }
    145     void add(int l,int r,int k)
    146     {
    147         splay(get_k(l),0);
    148         splay(get_k(r+2),root);
    149         lz1[key_value]+=k;
    150         s[key_value]+=k;
    151         key[key_value]+=k;
    152         pushup(ch[root][1]);
    153         pushup(root);
    154     }
    155     LL query(int l,int r)
    156     {
    157         splay(get_k(l),0);
    158         splay(get_k(r+2),root);
    159         return s[key_value];
    160     }
    161     void reverse(int l,int r)
    162     {
    163         splay(get_k(l),0);
    164         splay(get_k(r+2),root);
    165         lz2[key_value]^=1;
    166         pushup(ch[root][1]);
    167         pushup(root);
    168     }
    169     void revolve(int l,int r,int k)
    170     {
    171         splay(get_k(r-k+1),0);
    172         splay(get_k(r+2),root);
    173         int nod = key_value;
    174         key_value = 0;
    175         pushup(ch[root][1]);
    176         pushup(root);
    177 
    178         splay(get_k(l),0);
    179         splay(get_k(l+1),root);
    180         key_value = nod;
    181         pre[nod] = ch[root][1];
    182         pushup(ch[root][1]);
    183         pushup(root);
    184     }
    185     void insert(int k,int p)
    186     {
    187         splay(get_k(k),0);
    188         splay(get_k(k+1),root);
    189         newnode(key_value,p,ch[root][1]);
    190         pushup(ch[root][1]);
    191         pushup(root);
    192     }
    193     void updelete(int k)
    194     {
    195         splay(get_k(k),0);
    196         splay(get_k(k+2),root);
    197         key_value = 0;
    198         pushup(ch[root][1]);
    199         pushup(root);
    200     }
    201     void build(int &x,int l,int r,int fa)
    202     {
    203         int m = (l+r)>>1;
    204         if(l>r) return ;
    205         newnode(x,a[m],fa);
    206         build(ch[x][0],l,m-1,x);
    207         build(ch[x][1],m+1,r,x);
    208         pushup(x);
    209     }
    210     void init(int o)
    211     {
    212         int i;
    213         for(i = 1; i <= o ; i++)
    214             scanf("%d",&a[i]);
    215         size[0] = ch[0][0] = ch[0][1] =  key[0] = lz1[0] = lz2[0] = s[0] = 0;
    216         root = tot = 0;
    217         newnode(root,0,0);
    218         newnode(ch[root][1],0,root);
    219         build(ch[ch[root][1]][0],1,o,ch[root][1]);
    220         size[root] = 2;
    221         pushup(ch[root][1]);
    222         pushup(root);
    223     }
    224 //    void work()
    225 //    {
    226 //        for(int i =  1; i <= size[root] ;i++)
    227 //        cout<<key[get_k(i)]<<" ";
    228 //        puts("");
    229 //    }
    230 } SP;
    231 int main()
    232 {
    233     int n,q,k,x,y;
    234     char sq[10];
    235     while(scanf("%d",&n)!=EOF)
    236     {
    237         SP.init(n);
    238         scanf("%d",&q);
    239         while(q--)
    240         {
    241             scanf("%s",sq);
    242             if(sq[0]=='A')
    243             {
    244                 scanf("%d%d%d",&x,&y,&k);
    245                 SP.add(x,y,k);
    246             }
    247             else if(strcmp(sq,"REVERSE")==0)
    248             {
    249                 scanf("%d%d",&x,&y);
    250                 SP.reverse(x,y);
    251             }
    252             else if(strcmp(sq,"REVOLVE")==0)
    253             {
    254                 scanf("%d%d%d",&x,&y,&k);
    255                 if(k<=0) continue;
    256                 k = k%(y-x+1);
    257                 SP.revolve(x,y,k);
    258             }
    259             else if(sq[0]=='I')
    260             {
    261                 scanf("%d%d",&k,&x);
    262                 SP.insert(k+1,x);
    263             }
    264             else if(sq[0]=='D')
    265             {
    266                 scanf("%d",&k);
    267                 SP.updelete(k);
    268             }
    269             else if(sq[0]=='M')
    270             {
    271                 scanf("%d%d",&x,&y);
    272                 printf("%d
    ",SP.query(x,y));
    273             }
    274             //SP.work();
    275         }
    276     }
    277     return 0;
    278 }
    View Code
  • 相关阅读:
    hdu 1754 线段树 注意线段树节点的设计 求什么,设什么
    hdu 4015 概率题
    poj 1950 回溯
    最大上升子序列
    JVM学习博客
    2012
    i am alone at a crossroads
    易知难
    牢骚。。
    something
  • 原文地址:https://www.cnblogs.com/shangyu/p/3796675.html
Copyright © 2020-2023  润新知