• Splay的用法


    splay区间增减查询

     1 #include<cstdio>
     2 #include<algorithm>
     3 
     4 using namespace std;
     5 
     6 const int N = 500100;
     7 const int INF = 1e9;
     8 typedef long long LL;
     9 int sum[N],data[N],siz[N],tag[N],ch[N][2],fa[N],st[N];
    10 int Root,top;
    11 
    12 inline int read() {
    13     int x = 0,f = 1;char ch = getchar();
    14     for (; ch<'0'||ch>'9'; ch = getchar())
    15         if (ch=='-') f = -1;
    16     for (; ch>='0'&&ch<='9'; ch = getchar())
    17         x = x * 10 + ch - '0';
    18     return x * f;
    19 }
    20 inline void pushup(int x) {
    21     int l = ch[x][0],r = ch[x][1];
    22     siz[x] = siz[l] + siz[r] + 1;
    23     sum[x] = sum[l] + sum[r] + data[x];
    24 }
    25 inline void pushdown(int x) {
    26     if (tag[x]) {
    27         int l = ch[x][0],r = ch[x][1];
    28         sum[l] += siz[l] * tag[x];sum[r] += siz[r] * tag[x];
    29         data[l] += tag[x];data[r] += tag[x];
    30         tag[l] += tag[x];tag[r] += tag[x];
    31         tag[x] = 0;
    32     }
    33 }
    34 inline int son(int x) {
    35     return x==ch[fa[x]][1];
    36 }
    37 inline void rotate(int x) {
    38     int y = fa[x],z = fa[y],b = son(x),c = son(y),a = ch[x][!b];
    39     if (z) ch[z][c] = x;else Root = x;fa[x] = z;
    40     ch[x][!b] = y;fa[y] = x;
    41     ch[y][b] = a;if (a) fa[a] = y;
    42     pushup(y),pushup(x);
    43 }
    44 inline void splay(int x,int rt) {
    45     top = 0;int p = x;
    46     while (p) st[++top] = p,p = fa[p];
    47     while (top) pushdown(st[top]),top--;
    48     while (fa[x] != rt) {
    49         int y =fa[x],z = fa[y];
    50         if (z==rt) rotate(x);
    51         else {
    52             if (son(x)==son(y)) rotate(y),rotate(x);
    53             else rotate(x),rotate(x);
    54         }
    55     }
    56 }
    57 inline void update(int L,int R,int a) {
    58     splay(L,0);splay(R,L);
    59     tag[ch[R][0]] += a;
    60     sum[ch[R][0]] += siz[ch[R][0]] * a;
    61     data[ch[R][0]] += a;
    62     pushup(R),pushup(L);
    63 }
    64 inline int query(int L,int R) {
    65     splay(L,0);splay(R,L);
    66     return sum[ch[R][0]];
    67 }
    68 int build(int l,int r) {
    69     if (l > r) return 0;
    70     if (l==r) {
    71         siz[l] = 1;sum[l] = data[l];return l;
    72     }
    73     int mid = (l + r) >> 1;
    74     int t = build(l,mid-1);
    75     fa[t] = mid;ch[mid][0] = t;
    76     t = build(mid+1,r);
    77     fa[t] = mid;ch[mid][1] = t;
    78     pushup(mid);
    79     return mid;
    80 }
    81 int main() {
    82     int n = read(),m = read();
    83     for (int i=2; i<=n+1; ++i) data[i] = read();
    84     Root = build(1,n+2);
    85     fa[0] = 0;
    86     //char s[10];
    87     for (int o,a,b,c,i=1; i<=m; ++i) {
    88         o = read();
    89         if (o == 1) {
    90             a = read(),b = read(),c = read();
    91             update(a,b+2,c);
    92         }
    93         else {
    94             a = read(),b = read();
    95             printf("%d
    ",query(a,b+2));
    96         }
    97     }
    98     return 0;
    99 }
    View Code
  • 相关阅读:
    oracle trunc()函数的用法——日期、数字
    ORACLE定时任务时间间隔设置
    Oracle JOB 间隔时间详解
    "规格"与"数量"的英文缩写是什么
    “金额”“合计”用英语怎么说?有什么区别么?
    关于狼性的团队励志名言警句
    5篇关于职场技巧的励志文章
    菜单权限分配源码奉送V2.0
    安装 SQL Server 客户端驱动程序
    一步步开发自己的博客 .NET版(9、从model first替换成code first 问题记录)
  • 原文地址:https://www.cnblogs.com/mjtcn/p/8010933.html
Copyright © 2020-2023  润新知