HDU_4267

    根据k的值建立10类树状数组,每类中根据i%k的不同建立k棵树状数组,也就是55棵树状数组,这样每次修改操作只对其中1棵树状数组进行操作,所以是O(logN)的复杂度,每次查询只对其中10棵树状数组统计增量和,所以是O(10*logN)的复杂度。

#include<stdio.h>
#include<string.h>
#define MAXD 50010
int N, M, d[100][MAXD], a[MAXD];
void insert(int k, int x, int v)
{
    for(; x <= N; x += x & -x) d[k][x] += v;
}
void init()
{
    int i, j;
    for(i = 1; i <= N; i ++) scanf("%d", &a[i]);
    for(i = 0; i < 100; i ++) memset(d[i], 0, sizeof(d[i][0]) * (N + 1));
}
int query(int id)
{
    int i, k, x, ans = 0;
    for(i = 1; i <= 10; i ++)
    {
        k = (i - 1) * 10 + id % i;
        for(x = id; x > 0; x -= x & -x) ans += d[k][x];
    }
    return a[id] + ans;
}
void solve()
{
    int i, op, a, b, k, c;
    scanf("%d", &M);
    for(i = 0; i < M; i ++)
    {
        scanf("%d", &op);
        if(op == 1)
        {
            scanf("%d%d%d%d", &a, &b, &k, &c);
            b -= (b - a) % k;
            insert(10 * (k - 1) + a % k, a, c);
            if(b < N) insert(10 * (k - 1) + b % k, b + 1, -c);
        }
        else if(op == 2)
        {
            scanf("%d", &a);
            printf("%d\n", query(a));
        }
    }
}
int main()
{
    while(scanf("%d", &N) == 1)
    {
        init();
        solve();
    }
    return 0;
}
posted on 2012-09-08 21:33  Staginner  阅读(1485)  评论(0编辑  收藏  举报