• [BZOJ1176][Balkan2007]Mokia


    1176: [Balkan2007]Mokia

    Time Limit: 30 Sec  Memory Limit: 162 MB
    Submit: 2633  Solved: 1184
    [Submit][Status][Discuss]

    Description

    维护一个W*W的矩阵,初始值均为S.每次操作可以增加某格子的权值,或询问某子矩阵的总权值.修改操作数M<=160000,询问数Q<=10000,W<=2000000.

    Input

    第一行两个整数,S,W;其中S为矩阵初始值;W为矩阵大小

    接下来每行为一下三种输入之一(不包含引号):

    "1 x y a"

    "2 x1 y1 x2 y2"

    "3"

    输入1:你需要把(x,y)(第x行第y列)的格子权值增加a

    输入2:你需要求出以左下角为(x1,y1),右上角为(x2,y2)的矩阵内所有格子的权值和,并输出

    输入3:表示输入结束

    Output

    对于每个输入2,输出一行,即输入2的答案

    Sample Input

    0 4
    1 2 3 3
    2 1 1 3 3
    1 2 2 2
    2 2 2 3 4
    3

    Sample Output

    3
    5

    HINT

    保证答案不会超过int范围

    CDQ分治

    还是把每种查询拆成四个

    然后时间直接不用排了。。

    在分治过程中按照$x$归并,然后一边归并一边把$y$加到权值树状数组里面

    树状数组清空可以打时间戳

    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    using namespace std;
    char buf[10000000], *ptr = buf - 1;
    inline int readint() {
        int f = 1, n = 0;
        char ch = *++ptr;
        while (ch < '0' || ch > '9') {
            if (ch == '-') f = -1;
            ch = *++ptr;
        }
        while (ch <= '9' && ch >= '0') {
            n = (n << 1) + (n << 3) + ch - '0';
            ch = *++ptr;
        }
        return f * n;
    }
    int s, w;
    int C[2000000 + 10], T[2000000 + 10] = { 0 }, flag = 0;
    inline int Query(int pos) {
        int ret = 0;
        for (int i = pos; i; i -= i & -i)
            if (T[i] == flag) ret += C[i];
        return ret;
    }
    inline void Update(int pos, int val) {
        for(int i = pos; i <= w; i += i & -i)
            if (T[i] != flag) {
                T[i] = flag;
                C[i] = val;
            }
            else C[i] += val;
    }
    struct Que {
        int type, x, y, val;
        Que() {}
        Que(int _type, int _x, int _y, int _val) : type(_type), x(_x), y(_y), val(_val) {}
    }q[200000 + 10], tp[200000 + 10];
    int ans[10000 + 10] = {0};
    void CDQ(int l, int r) {
        if (l == r) return;
        int mid = l + r >> 1, ll = l, rr = mid + 1, tcnt = 0;
        CDQ(l, mid); CDQ(mid + 1, r);
        flag++;
        while (ll <= mid && rr <= r) {
            if (q[ll].x <= q[rr].x) {
                if (q[ll].type == 1) Update(q[ll].y, q[ll].val);
                tp[++tcnt] = q[ll++];
            }
            else {
                if (q[rr].type == 2) ans[q[rr].val] += Query(q[rr].y);
                else if(q[rr].type == 3) ans[q[rr].val] -= Query(q[rr].y);
                tp[++tcnt] = q[rr++];
            }
        }
        while (ll <= mid) tp[++tcnt] = q[ll++];
        while (rr <= r) {
            if (q[rr].type == 2) ans[q[rr].val] += Query(q[rr].y);
            else if(q[rr].type == 3) ans[q[rr].val] -= Query(q[rr].y);
            tp[++tcnt] = q[rr++];
        }
        for (int i = 1; i <= tcnt; i++) q[l + i - 1] = tp[i];
    }
    int sz = 0;
    int main() {
        fread(buf, sizeof(char), sizeof(buf), stdin);
        s = readint();
        w = readint();
        int opt, x1, y1, x2, y2, a, qtime = 0;
        while ((opt = readint()) != 3) {
            x1 = readint();
            y1 = readint();
            if (opt == 1) {
                a = readint();
                q[++sz] = Que(1, x1, y1, a);
            }
            else {
                qtime++;
                x2 = readint();
                y2 = readint();
                q[++sz] = Que(2, x2, y2, qtime);
                q[++sz] = Que(2, x1 - 1, y1 - 1, qtime);
                q[++sz] = Que(3, x1 - 1, y2, qtime);
                q[++sz] = Que(3, x2, y1 - 1, qtime);
            //    ans[qtime] = (x2 - x1 + 1) * (y2 - y1 + 1) * s;
            }
        }
        CDQ(1, sz);
        for (int i = 1; i <= qtime; i++)
            printf("%d
    ", ans[i]);
        return 0;
    }
  • 相关阅读:
    程序、进程、线程区别与联系
    SQL常用知识与必须掌握的面试常问SQL语句
    快速搭建一个基于react的项目
    原生js判断设备类型
    在vue项目中设置BASE_URL
    纯前端实现数据导出excel文件
    原生js实现拖拽功能
    使用Echarts实现折线图的一点总结
    在vue项目中显示实时时间(年月日时分秒)
    在vue项目中使用MD5.js
  • 原文地址:https://www.cnblogs.com/ruoruoruo/p/7612794.html
Copyright © 2020-2023  润新知