暑假前专题题解---数据结构---B

线段树的基本区间操作

#include<bits/stdc++.h>

using namespace std;

typedef long long LL;

const int maxn = 1e6 + 10;

LL sum[maxn<<2],p[maxn<<2];

LL sum1;

void up(int id){

    sum[id] = sum[id<<1] + sum[id<<1|1];

}

void down(int l,int r,int id){

    int mid = (l + r) >> 1;

    if (p[id]){

        p[id<<1] += p[id];

        p[id<<1|1] += p[id];

        sum[id<<1] += p[id]*(mid-l+1);

        sum[id<<1|1] += p[id]*(r-mid);

        p[id] = 0;

    }

}

void rev(int l,int r,int id,int L,int R,int c){

    if (L <= l && r <= R){

        p[id] += c;

        sum[id] += (r - l + 1) * c;

        return ;

    }

    int mid = (l + r) >> 1;

    down(l, r, id);

    if (L <= mid) rev(l, mid, id<<1, L, R, c);

    if (R > mid) rev(mid+1, r, id<<1|1, L, R, c);

    up(id);

}

void query(int l,int r,int id,int L,int R){

    if (L <= l && r <= R){

        sum1 += sum[id];

        return;

    }

    int mid = (l + r) >> 1;

    down(l,r,id);

    if (L <= mid) query(l, mid, id<<1, L, R);

    if (R > mid) query(mid+1, r, id<<1|1, L, R);

}

int main(){

    int n,m,o,l,r,v;

    scanf("%d%d",&n,&m);

    for (int i=0; i<m; i++) {

        scanf("%d %d %d %d",&o,&l,&r,&v);

        if (o == 0) rev(1, n, 1, l, r, v);

        else{

            query(1, n, 1, l, r);

            printf("%lld\n",sum1);

            sum1 = 0;

        }

    }

    return 0;

}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值