zoukankan      html  css  js  c++  java
  • UVA 11992 线段树

    input

    r c m      r<=20,1<=m<=20000

    m行操作

    1 x1 y1 x2 y2 v       add v

    2 x1 y1 x2 y2 v       set v

    3 x1 y1 x2 y2   查询该矩阵中的sum,max,min

    output

    对于每个3操作输出sum,max,min

    做法:每行建一颗线段树

      1 #include <cstdio>
      2 #include <queue>
      3 #include <cstring>
      4 #include <iostream>
      5 #include <cstdlib>
      6 #include <algorithm>
      7 #include <vector>
      8 #include <map>
      9 #include <set>
     10 #include <ctime>
     11 #include <cmath>
     12 #define INF 0x7fffffff
     13 #define MAX 1000000
     14 
     15 using namespace std;
     16 
     17 struct node
     18 {
     19     int v,addv,setv,sum,min,max;
     20 };
     21 int r,c,m,x1,yy1,x2,yy2,v,op,suma,mina,maxa;
     22 node a[21][MAX*3];
     23 void pushdown(int &l,int &r,int &k,int&i)
     24 {
     25     if(a[i][k].setv==0&&a[i][k].addv==0) return;
     26     int m=l+((r-l)>>1),lc=k<<1,rc=k<<1|1,allv=a[i][k].setv+a[i][k].addv;
     27     if(a[i][k].setv)        //有set操作时优先将set操作pushdown
     28     {
     29         a[i][lc].addv=a[i][rc].addv=a[i][k].addv;
     30         a[i][lc].v=a[i][rc].v=a[i][lc].setv=a[i][rc].setv=a[i][k].setv;
     31         a[i][lc].min=a[i][rc].min=a[i][lc].max=a[i][rc].max=allv;
     32         a[i][lc].sum=(m-l+1)*allv;
     33         a[i][rc].sum=(r-m)*allv;
     34         a[i][k].setv=a[i][k].addv=0;
     35     }
     36     else                    //无set操作时只是add操作也要pushdown
     37     {
     38         a[i][lc].addv+=a[i][k].addv;
     39         a[i][rc].addv+=a[i][k].addv;
     40         a[i][lc].min+=a[i][k].addv;
     41         a[i][rc].min+=a[i][k].addv;
     42         a[i][lc].max+=a[i][k].addv;
     43         a[i][rc].max+=a[i][k].addv;
     44         a[i][lc].sum+=(m-l+1)*a[i][k].addv;
     45         a[i][rc].sum+=(r-m)*a[i][k].addv;
     46         a[i][k].addv=0;
     47     }
     48 //    printf("l:%d r:%d setv:%d add:%d
    ",l,r,a[i][k].setv,a[i][k].addv);
     49 }
     50 void reset(int &l,int &r,int &k,int&i)
     51 {
     52     int m=l+((r-l)>>1),lc=k<<1,rc=k<<1|1;
     53     a[i][k].sum=a[i][lc].sum+a[i][rc].sum+(r-l+1)*a[i][k].addv;
     54     a[i][k].min=min(a[i][lc].min,a[i][rc].min)+a[i][k].addv;
     55     a[i][k].max=max(a[i][lc].max,a[i][rc].max)+a[i][k].addv;
     56 }
     57 void setupdate(int l,int r,int k,int &i)
     58 {
     59     int lc=k<<1,rc=k<<1|1;
     60     if(yy1<=l&&yy2>=r)
     61     {
     62         a[i][k].min=a[i][k].max=a[i][k].setv=a[i][k].v=v;
     63         a[i][k].addv=0;
     64         a[i][k].sum=(r-l+1)*v;
     65     //printf("l:%d r:%d setv:%d add:%d
    ",l,r,a[i][k].setv,a[i][k].addv);
     66         return;
     67     }
     68     pushdown(l,r,k,i);
     69     int m=l+((r-l)>>1);
     70     if(yy1<=m) setupdate(l,m,lc,i);
     71     if(yy2>m) setupdate(m+1,r,rc,i);
     72     reset(l,r,k,i);
     73 }
     74 void addupdate(int l,int r,int k,int &i)
     75 {
     76     int lc=k<<1,rc=k<<1|1;
     77     if(yy1<=l&&yy2>=r)
     78     {
     79         a[i][k].addv+=v;
     80         a[i][k].sum+=(r-l+1)*v;
     81         a[i][k].min+=v;
     82         a[i][k].max+=v;
     83         return;
     84     }
     85     pushdown(l,r,k,i);
     86     int m=l+((r-l)>>1);
     87     if(yy1<=m) addupdate(l,m,lc,i);
     88     if(yy2>m) addupdate(m+1,r,rc,i);
     89     reset(l,r,k,i);
     90 }
     91 void query(int l,int r,int k,int& i,int add)
     92 {
     93     if(a[i][k].setv)
     94     {
     95         int allv=add+a[i][k].v+a[i][k].addv;
     96         suma+=allv*(min(r,yy2)-max(l,yy1)+1);
     97         mina=min(mina,allv);
     98         maxa=max(maxa,allv);
     99         //printf("addv:%d all:%d %d %d
    ",a[i][k].addv,add,mina,maxa);
    100         return;
    101     }
    102     if(yy1<=l&&yy2>=r)
    103     {
    104         suma+=a[i][k].sum+(r-l+1)*add;
    105         mina=min(mina,a[i][k].min+add);
    106         maxa=max(maxa,a[i][k].max+add);
    107         return;
    108     }
    109     int m=l+((r-l)>>1);
    110     if(yy1<=m) query(l,m,k<<1,i,add+a[i][k].addv);
    111     if(yy2>m) query(m+1,r,k<<1|1,i,add+a[i][k].addv);
    112 }
    113 int main()
    114 {
    115     freopen("/home/user/桌面/in","r",stdin);
    116     while(scanf("%d%d%d",&r,&c,&m)==3)
    117     {
    118         for(int i=1;i<=r;i++) memset(a[i],0,sizeof(a[0][0])*3*c);
    119         //memset(a,0,sizeof(a));
    120         while(m--)
    121         {
    122             scanf("%d%d%d%d%d",&op,&x1,&yy1,&x2,&yy2);
    123             if(op==2)
    124             {
    125                 scanf("%d",&v);
    126                 for(int i=x1;i<=x2;i++) setupdate(1,c,1,i);
    127                 //for(int i=1;i<3*c;i++) printf("%d:%d %d
    ",i,a[3][i].setv,a[3][i].addv);
    128                 //puts("set");
    129             }
    130             else if(op==1)
    131             {
    132                 scanf("%d",&v);
    133                 for(int i=x1;i<=x2;i++) addupdate(1,c,1,i);
    134                 //for(int i=1;i<3*c;i++) printf("%d:%d %d
    ",i,a[3][i].setv,a[3][i].addv);
    135                 //puts("add");
    136             }
    137             else
    138             {
    139                 suma=0;
    140                 mina=INF;
    141                 maxa=-INF-1;
    142                 //printf("row:%d-%d
    col:%d-%d
    ",x1,x2,yy1,yy2);
    143                 //for(int i=1;i<=r;i++) printf("rowsum:%d
    ",a[i][1].sum);
    144                 for(int i=x1;i<=x2;i++) query(1,c,1,i,0);
    145                 printf("%d %d %d
    ",suma,mina,maxa);
    146             }
    147         }
    148     }
    149     //printf("time=%.3lf",(double)clock()/CLOCKS_PER_SEC);
    150     return 0;
    151 }
    View Code
  • 相关阅读:
    持续集成-禅道
    nohup.out 日志切分
    Flannel 介绍及使用场景
    【Unity游戏开发】初探Unity动画优化
    fastHttp服务端处理请求的过程
    PHPExcel导出文件代码实现
    PHPExcel 1.8
    CKfinder 安装与使用
    Ckeditor的配置
    Ckeditor的使用
  • 原文地址:https://www.cnblogs.com/cdyboke/p/4989587.html
Copyright © 2011-2022 走看看