zoukankan      html  css  js  c++  java
  • BZOJ 2716/2648 SJY摆棋子 (三维偏序CDQ+树状数组)

    题目大意:

    洛谷传送门

    这明明是一道KD-Tree,CDQ分治是TLE的做法

    化简式子,$|x1-x2|-|y1-y2|=(x1+y1)-(x2+y2)$

    而$CDQ$分治只能解决$x1 leq x2,y1 leq y2$的情况

    把每次插入操作都相当于一个三元组$<x,y,t>$,权值是$x+y$。这就是一个三维偏序问题,用树状数组维护最大值即可

    所以通过坐标变换,跑$4$次$CDQ$就行了?

    没错,你会像我一样T得飞起

     1 #include <cstdio>
     2 #include <cstring>
     3 #include <algorithm>
     4 #define N1 1001000
     5 #define M1 1001000
     6 #define ll long long
     7 #define dd double
     8 #define inf 233333333
     9 using namespace std;
    10 
    11 int gint()
    12 {
    13     int ret=0,fh=1;char c=getchar();
    14     while(c<'0'||c>'9'){if(c=='-')fh=-1;c=getchar();}
    15     while(c>='0'&&c<='9'){ret=ret*10+c-'0';c=getchar();}
    16     return ret*fh;
    17 }
    18 int n,m,ma,nm,mx,my;
    19 struct BIT{
    20 int ma[M1];
    21 void update(int x,int w){ for(int i=x;i<=my;i+=(i&(-i))) ma[i]=max(ma[i],w); }
    22 int query(int x){ int ans=-inf; for(int i=x;i;i-=(i&(-i))) ans=max(ans,ma[i]); return ans; }
    23 void clr(int x){ for(int i=x;i<=my;i+=(i&(-i))) ma[i]=-inf;}
    24 void init(){ for(int i=1;i<=my;i++) ma[i]=-inf; }
    25 }s;
    26 struct node{int x,y,p,t,ans;}a[N1],tmp[N1];
    27 int cmp1(node s1,node s2){ if(s1.x!=s2.x) return s1.x<s2.x; if(s1.y!=s2.y) return s1.y<s2.y; return s1.p<s2.p;}
    28 int cmpt(node s1,node s2){ return s1.t<s2.t; }
    29 int que[N1],tl;
    30 
    31 void CDQ(int L,int R)
    32 {
    33     if(R-L<=1) return;
    34     int i,j,k,M=(L+R)>>1;
    35     for(i=L,j=M,k=L;k<R;k++)
    36     {
    37         if(a[k].t<M) tmp[i++]=a[k];
    38         else tmp[j++]=a[k];
    39     }
    40     for(k=L;k<R;k++) a[k]=tmp[k];
    41     CDQ(L,M);
    42     for(i=L,j=M;i<M&&j<R;)
    43     {
    44         if(cmp1(a[i],a[j])){ if(a[i].p==1) { s.update(a[i].y,a[i].x+a[i].y); que[++tl]=i; } i++; }
    45         else{ if(a[j].p==2) a[j].ans=min(a[j].ans,(a[j].x+a[j].y)-s.query(a[j].y)); j++; }
    46     }
    47     while(j<R){ if(a[j].p==2) a[j].ans=min(a[j].ans,(a[j].x+a[j].y)-s.query(a[j].y)); j++; }
    48     while(tl){ s.clr(a[que[tl--]].y); }
    49     CDQ(M,R);
    50     for(i=L,j=M,k=0;i<M&&j<R;)
    51     {
    52         if(cmp1(a[i],a[j])) tmp[++k]=a[i++];
    53         else tmp[++k]=a[j++];
    54     }
    55     while(i<M){ tmp[++k]=a[i++]; }
    56     while(j<R){ tmp[++k]=a[j++]; }
    57     for(k=L;k<R;k++) a[k]=tmp[k-L+1];
    58 }
    59 int p[N1];
    60 
    61 int main()
    62 {
    63     int i,j; n=gint(); m=gint(); nm=n+m;
    64     for(i=1;i<=n;i++){ a[i].p=1; a[i].x=gint()+1; a[i].y=gint()+1; a[i].t=i; a[i].ans=inf; mx=max(mx,a[i].x); my=max(my,a[i].y); }
    65     for(i=n+1;i<=n+m;i++){ a[i].p=gint(); a[i].x=gint()+1; a[i].y=gint()+1; a[i].t=i; a[i].ans=inf; mx=max(mx,a[i].x); my=max(my,a[i].y); }
    66     sort(a+1,a+nm+1,cmp1); s.init();
    67     CDQ(1,nm+1); 
    68     for(i=1;i<=nm;i++){ a[i].x=mx-a[i].x+1; } sort(a+1,a+nm+1,cmp1); 
    69     CDQ(1,nm+1); 
    70     for(i=1;i<=nm;i++){ a[i].y=my-a[i].y+1; } sort(a+1,a+nm+1,cmp1); 
    71     CDQ(1,nm+1); 
    72     for(i=1;i<=nm;i++){ a[i].x=mx-a[i].x+1; } sort(a+1,a+nm+1,cmp1); 
    73     CDQ(1,nm+1); 
    74     sort(a+1,a+nm+1,cmpt);
    75     for(i=n+1;i<=nm;i++) if(a[i].p==2) printf("%d
    ",a[i].ans);
    76     return 0;
    77 }
  • 相关阅读:
    模拟ajax请求爬取微博
    使用nohup+& 踩到的坑
    Python3爬虫一之(urllib库)
    在linux下安装并运行scrapyd
    创建Django项目并将其部署在腾讯云上
    python解析库之 XPath
    python3中urllib库的request模块详解
    HTTP协议详解
    线程之红绿灯
    win7 64 下安装MyGeneration 遇到的问题解决方法
  • 原文地址:https://www.cnblogs.com/guapisolo/p/10211320.html
Copyright © 2011-2022 走看看