zoukankan      html  css  js  c++  java
  • bzoj2683简单题 cdq分治

    2683: 简单题

    Time Limit: 50 Sec  Memory Limit: 128 MB
    Submit: 1803  Solved: 731
    [Submit][Status][Discuss]

    Description

    你有一个N*N的棋盘,每个格子内有一个整数,初始时的时候全部为0,现在需要维护两种操作:

    命令

    参数限制

    内容

    1 x y A

    1<=x,y<=N,A是正整数

    将格子x,y里的数字加上A

    2 x1 y1 x2 y2

    1<=x1<= x2<=N

    1<=y1<= y2<=N

    输出x1 y1 x2 y2这个矩形内的数字和

    3

    终止程序

    Input

    输入文件第一行一个正整数N。
    接下来每行一个操作。
     

    Output

    对于每个2操作,输出一个对应的答案。
     

    Sample Input

    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

    1<=N<=500000,操作数不超过200000个,内存限制20M。

    对于100%的数据,操作1中的A不超过2000。

    cdq分治三维偏序 三维分别是操作序号,横坐标,纵坐标
    把一个询问拆成4个,就变成了处理二维前缀和问题
    对横坐标排序,操作序号cdq分治,纵坐标用bit处理

     1 #include<bits/stdc++.h>
     2 #define N 200005
     3 using namespace std;
     4 int n,m,t,c[N*3],ans[N];
     5 struct query{
     6     int x,y,v,id,op,bl;
     7     bool operator < (const query &b)const{
     8         if(x==b.x&&y==b.y)return id<b.id;
     9         return x==b.x?y<b.y:x<b.x;
    10     }
    11 }q[N<<2],a[N<<2];
    12 
    13 void add(int x,int y,int v){
    14     if(!x||!y)return;
    15     q[++m].x=x;q[m].y=y;q[m].id=m;
    16     q[m].op=2;q[m].bl=t;q[m].v=v;
    17 }
    18 void update(int p,int x){
    19     while(p<=n){
    20         c[p]+=x;
    21         p+=p&-p;
    22     }
    23 }
    24 int ask(int x){
    25     int ret=0;
    26     while(x){
    27         ret+=c[x];
    28         x-=x&-x;
    29     }
    30     return ret;
    31 }
    32 
    33 void solve(int l,int r){
    34     if(l==r)return;
    35     int mid=(l+r)>>1,p1=l,p2=mid+1;
    36     for(int i=l;i<=r;++i){
    37         if(q[i].id<=mid&&q[i].op==1)update(q[i].y,q[i].v);
    38         if(q[i].id>mid&&q[i].op==2)ans[q[i].bl]+=ask(q[i].y)*q[i].v;
    39     }
    40     for(int i=l;i<=r;++i)
    41     if(q[i].op==1&&q[i].id<=mid)update(q[i].y,-q[i].v);
    42     for(int i=l;i<=r;++i){
    43         if(q[i].id<=mid)a[p1++]=q[i];
    44         else a[p2++]=q[i];
    45     }
    46     for(int i=l;i<=r;++i)q[i]=a[i];
    47     solve(l,mid);solve(mid+1,r);
    48 }
    49 int main(){
    50     scanf("%d",&n);
    51     while(1){
    52         static int op,x1,x2,y1,y2,v;
    53         scanf("%d",&op);
    54         if(op==1){
    55             scanf("%d%d%d",&x1,&y1,&v);
    56             q[++m].x=x1;q[m].y=y1;q[m].v=v;
    57             q[m].id=m;q[m].op=op;
    58         }
    59         if(op==2){
    60             scanf("%d%d%d%d",&x1,&y1,&x2,&y2);++t;
    61             add(x1-1,y1-1,1);add(x2,y2,1);
    62             add(x1-1,y2,-1);add(x2,y1-1,-1);
    63         }
    64         if(op==3)break;
    65     } 
    66     sort(q+1,q+1+m);
    67     solve(1,m);
    68     for(int i=1;i<=t;i++)
    69     printf("%d
    ",ans[i]);
    70     return 0;
    71 }
  • 相关阅读:
    百度笔试题:找最小的不重复数
    [置顶] 【收藏】实用软件
    指针数组与数组指针
    根据新浪天气API获取各地天气状况(Java实现)
    项目经历——EasyUI的检索和更新操作
    利用MyEclipse配置S2SH三大框架篇-Spring配置
    Intellij IDEA 最头大的问题,如何自定义注释模板?
    Spring Cloud Gateway VS Zuul 比较,怎么选择?
    Spring Boot 注册 Servlet 的三种方法,真是太有用了!
    Spring Cloud Eureka 常用配置详解,建议收藏!
  • 原文地址:https://www.cnblogs.com/wsy01/p/8169064.html
Copyright © 2011-2022 走看看