zoukankan      html  css  js  c++  java
  • POJ3468——树状数组支持两个区间操作

    题目:http://poj.org/problem?id=3468

    推断过程可自己查,得式子:fixsum(x) = (x+1) * ∑(i=1,x)fi - ∑(i=1,x)i*fi;

    其中 f 是真实值的修改量,故修改区间变为f的单点修改,求真实值时取f的前缀和加上自己的原值(真实值)。

    故修改i*fi时也是普通的单点修改,再普通维护树状数组,每个影响的部分和都加上这个固定值。

    最后求前缀和时用fixsum加上原前缀和得到修改后的。

    #include<iostream>
    #include<cstdio>
    using namespace std;
    int n,t,L,R,c;
    long long a[100005],f[100005],fi[100005],s[100005];
    char ch;
    void add(int x,int c)
    {
        int y=x;
        for(;x<=n;x+=x&-x)
        {
            f[x]+=c;
            fi[x]+=y*c;
        }
    }
    long long query(int x)
    {
        long long fis=0,fs=0;
        int y=x;
        for(;x;x-=x&-x)
            fis+=fi[x],fs+=f[x];
        return (y+1)*fs-fis;
    }
    int main()
    {
        scanf("%d%d",&n,&t);
        for(int i=1;i<=n;i++)
        {
            scanf("%lld",&a[i]);
            s[i]=s[i-1]+a[i];
        }
        while(t--)
        {
            scanf(" %c",&ch);
            if(ch=='C')
            {
                scanf("%d%d%d",&L,&R,&c);
                add(L,c);add(R+1,-c);
            }
            else
            {
                scanf("%d%d",&L,&R);
                printf("%lld
    ",(query(R)+s[R])-(query(L-1)+s[L-1]));
            }
        }
        return 0;
    }
  • 相关阅读:
    内部类
    this关键字
    封装
    构造方法
    类图
    StringBuffer
    String
    导包
    包名规范
    带参数的方法
  • 原文地址:https://www.cnblogs.com/Narh/p/8439987.html
Copyright © 2011-2022 走看看