POJ - 1195 - Mobile phones (二维线段树)

Mobile phones

题目传送:Mobile phones

AC代码:

/************************************************
    > Auther        :  zzuspy
    > Mail          :  [email protected]
    > Created Time  :  2015/8/7 15:24:00
************************************************/
#include <map>
#include <set>
#include <list>
#include <cmath>
#include <deque>
#include <queue>
#include <stack>
#include <bitset>
#include <cctype>
#include <cstdio>
#include <string>
#include <vector>
#include <complex>
#include <cstdlib>
#include <cstring>
#include <fstream>
#include <sstream>
#include <utility>
#include <iostream>
#include <algorithm>
#include <functional>
#define LL long long
#define INF 0x7fffffff
using namespace std;

const int maxn = 1050;

int sum[maxn * 3][maxn * 3];

int S;//区间长度
int X, Y, A;
int L, B, R, T;

void add_x(int rty, int rtx, int L, int R, int x, int a) {//往rty这个区间找x轴的区间更新a
    sum[rty][rtx] += a;
    if(L == R) {
        return;
    }
    int mid = (L + R) >> 1;
    if(x <= mid) {
        add_x(rty, rtx << 1, L, mid, x, a);
    }
    else {
        add_x(rty, rtx << 1 | 1, mid + 1, R, x, a);
    }
}

void add_y(int rty, int L, int R, int x, int y, int a) {//在y轴上更新a
    add_x(rty, 1, 1, S, x, a);
    if(L == R) {
        return;
    }
    int mid = (L + R) >> 1;
    if(y <= mid) {
        add_y(rty << 1, L, mid, x, y, a);
    }
    else {
        add_y(rty << 1 | 1, mid + 1, R, x, y, a);
    }
}

int query_x(int rty, int rtx, int L, int R, int x1, int x2) {
    if(L >= x1 && R <= x2) {
        return sum[rty][rtx];
    }
    int ret = 0;
    int mid = (L + R) >> 1;
    if(x1 <= mid) ret += query_x(rty, rtx << 1, L, mid, x1, x2);
    if(x2 > mid) ret += query_x(rty, rtx << 1 | 1, mid + 1, R, x1, x2);
    return ret;
}

int query_y(int rty, int L, int R, int y1, int y2, int x1, int x2) {
    if(L >= y1 && R <= y2) {
        return query_x(rty, 1, 1, S, x1, x2);
    }
    int ret = 0;
    int mid = (L + R) >> 1;
    if(y1 <= mid) ret += query_y(rty << 1, L, mid, y1, y2, x1, x2);
    if(y2 > mid) ret += query_y(rty << 1 | 1, mid + 1, R, y1, y2, x1, x2);
    return ret;
}

int main() {
    int op;
    while(true) {
        scanf("%d", &op);
        switch(op) {
            case 0:
                scanf("%d", &S);
                memset(sum, 0, sizeof(sum));
                break;
            case 1:
                scanf("%d %d %d", &X, &Y, &A);
                add_y(1, 1, S, X + 1, Y + 1, A);
                break;
            case 2:
                scanf("%d %d %d %d", &L, &B, &R, &T);
                L ++, B ++, R ++, T++;
                printf("%d\n", query_y(1, 1, S, B, T, L, R));
                break;
            case 3:
                return 0;
        }
    }
    return 0;
}

版权声明:本文为博主原创文章,未经博主允许不得转载。

时间: 2024-11-04 20:11:19

POJ - 1195 - Mobile phones (二维线段树)的相关文章

poj1195 Mobile phones 二维线段树入门

二维线段树就是树套树,线段树套线段树... #include<iostream> #include<cstdio> #include<cstring> #include<cstdlib> #include<algorithm> #define REP(i,a,b) for(int i=a;i<=b;i++) #define MS0(a) memset(a,0,sizeof(a)) #define lson l,m,rt<<1 #

poj 1195 Mobile phones(二维数组)

#include<stdio.h> #include<string.h> #include<algorithm> using namespace std; int c[1048][1048],n; int lowbit[1048]; void add(int x,int y,int d) { int i,j; for(i=x;i<=n;i+=lowbit[i]) for(j=y;j<=n;j+=lowbit[j]) { c[i][j]+=d; } } int

POJ 2155 Matrix【二维线段树】

题目大意:给你一个全是0的N*N矩阵,每次有两种操作:1将矩阵中一个子矩阵置反,2.查询某个点是0还是1 思路:裸的二维线段树 #include<iostream>#include<cstdio>#include <math.h>#include<algorithm>#include<string.h>#include<queue>#define MOD 1000003#define maxn 4009#define LL long

poj 1195:Mobile phones(二维线段树,矩阵求和,经典题)

Mobile phones Time Limit: 5000MS   Memory Limit: 65536K Total Submissions: 14391   Accepted: 6685 Description Suppose that the fourth generation mobile phone base stations in the Tampere area operate as follows. The area is divided into squares. The

poj 1195:Mobile phones(二维树状数组,矩阵求和)

Mobile phones Time Limit: 5000MS   Memory Limit: 65536K Total Submissions: 14489   Accepted: 6735 Description Suppose that the fourth generation mobile phone base stations in the Tampere area operate as follows. The area is divided into squares. The

POJ1195 Mobile phones 【二维线段树】

Mobile phones Time Limit: 5000MS   Memory Limit: 65536K Total Submissions: 14291   Accepted: 6644 Description Suppose that the fourth generation mobile phone base stations in the Tampere area operate as follows. The area is divided into squares. The

POJ1195 Mobile phones 二维树状数组的应用

这题可以用线段树离散化做,用二维树状数组做了一下,不懂得可以看一下这篇文章:http://www.java3z.com/cwbwebhome/article/article1/1369.html?id=4804 题意: 给你一个s*s的正方形区域,先输入一个x,若x==0,则再输入一个s,若x==1,则输入x,y,a,表示矩阵中(x,y)这点的值加上a,若x==2,输入l,b,r,t,代表以左上角的点(l,b)右下角的点(r,t),求这一片矩形内的矩阵元素之和,若x==3则结束此次程序 就是最基

POJ 2155 二维线段树

POJ 2155  二维线段树 思路:二维线段树就是每个节点套一棵线段树的树. 刚开始因为题目是求A[I,J],然后在y查询那直接ans^=Map[i][j]的时候没看懂,后面自己把图画出来了才理解. 因为只有0和1,所以可以用异或来搞,而不需要每次都需要修改. #include<iostream> #include<cstdio> #include<cstring> #include<algorithm> #include<map> #incl

POJ 2155 二维线段树 经典的记录所有修改再统一遍历 单点查询

本来是想找一个二维线段树涉及懒惰标记的,一看这个题,区间修改,单点查询,以为是懒惰标记,敲到一半发现这二维线段树就不适合懒惰标记,你更新了某段的某列,但其实其他段的相应列也要打标记,但因为区间不一样,又不好打...也可能是我这是在套用一维线段树的思想,还有更好的二维线段树懒惰标记方法 反正到现在我还没搞定二维线段树的懒惰标记,因为这道题不用懒惰标记,因为是二进制序列,区间修改仅限于翻转操作,那就只要记录每次操作,最后查询的时候从上往下把所有修改都来上一遍,就可以了.就类似于树状数组的第二种用法,

POJ 2155 Matrix (二维线段树)

http://poj.org/problem?id=2155 Matrix Time Limit: 3000MS   Memory Limit: 65536K Total Submissions: 18143   Accepted: 6813 Description Given an N*N matrix A, whose elements are either 0 or 1. A[i, j] means the number in the i-th row and j-th column. I