zoukankan      html  css  js  c++  java
  • 【BZOJ】【2648】SJY摆棋子&【BZOJ】【2716】【Violet 3】天使玩偶

    KD-Tree


      传说中的kd树。。。前去膜拜了一下……写道模板题>_<

      

      写kdtree的一些感想:

      插入的时候是像可持久化线段树一样直接在最后开新节点,然后更新它所在的块。。
      然而其实也是用原来的叶子再分割一次这块区域?

      1 /**************************************************************
      2     Problem: 2716
      3     User: Tunix
      4     Language: C++
      5     Result: Accepted
      6     Time:16492 ms
      7     Memory:26280 kb
      8 ****************************************************************/
      9  
     10 //BZOJ 2716
     11 #include<cstdio>
     12 #include<cstring>
     13 #include<cstdlib>
     14 #include<iostream>
     15 #include<algorithm>
     16 #define rep(i,n) for(int i=0;i<n;++i)
     17 #define F(i,j,n) for(int i=j;i<=n;++i)
     18 #define D(i,j,n) for(int i=j;i>=n;--i)
     19 #define pb push_back
     20 using namespace std;
     21 typedef long long LL;
     22 inline int getint(){
     23     int r=1,v=0; char ch=getchar();
     24     for(;!isdigit(ch);ch=getchar()) if (ch=='-') r=-1;
     25     for(; isdigit(ch);ch=getchar()) v=v*10-'0'+ch;
     26     return r*v;
     27 }
     28 const int N=800010,INF=1e9;
     29 /*******************template********************/
     30  
     31 struct node{
     32     int d[2],mn[2],mx[2],l,r;
     33     int& operator [] (int x){return d[x];}
     34     void read(){d[0]=getint(); d[1]=getint();}
     35 }t[N],tmp;
     36 int n,m,D,root,ans,cnt;
     37  
     38 inline int dis(node a,node b){return abs(a[0]-b[0])+abs(a[1]-b[1]);}
     39 bool operator < (node a,node b){return a[D]<b[D] || (a[D]==b[D] && a[!D]<b[!D]);}
     40  
     41  
     42 #define L t[o].l
     43 #define R t[o].r
     44 #define mid (l+r>>1)
     45 void Push_up(int o){
     46     F(i,0,1){
     47         if (L){ t[o].mn[i]=min(t[o].mn[i],t[L].mn[i]); t[o].mx[i]=max(t[o].mx[i],t[L].mx[i]);}
     48         if (R){ t[o].mn[i]=min(t[o].mn[i],t[R].mn[i]); t[o].mx[i]=max(t[o].mx[i],t[R].mx[i]);}
     49     }
     50 }
     51  
     52 int build(int l,int r,int dir){
     53     D=dir;
     54     nth_element(t+l,t+mid,t+r+1);
     55     F(i,0,1) t[mid].mn[i]=t[mid].mx[i]=t[mid][i];
     56     if (l<mid) t[mid].l=build(l,mid-1,dir^1);
     57     if (r>mid) t[mid].r=build(mid+1,r,dir^1);
     58     Push_up(mid);
     59     return mid;
     60 }
     61  
     62 inline void Insert(int &o,int dir){
     63     if (!o){
     64         o=++cnt; t[o]=tmp;
     65         F(i,0,1) t[o].mn[i]=t[o].mx[i]=t[o][i];
     66         return;
     67     }
     68     if (tmp[dir]<t[o][dir]) Insert(L,dir^1);
     69     else Insert(R,dir^1);
     70     Push_up(o);
     71 }
     72  
     73 inline int getdis(int o){
     74     if (!o) return INF;
     75     int ans=0;
     76     F(i,0,1) ans+=max(0,t[o].mn[i]-tmp[i]);
     77     F(i,0,1) ans+=max(0,tmp[i]-t[o].mx[i]);
     78     return ans;
     79 }
     80  
     81 inline void query(int o){
     82     int dl=getdis(L),dr=getdis(R),d0=dis(t[o],tmp);
     83     ans=min(ans,d0);
     84     if (dl<dr){
     85         if (dl<ans) query(L);
     86         if (dr<ans) query(R);
     87     }else{
     88         if (dr<ans) query(R);
     89         if (dl<ans) query(L);
     90     }
     91 }
     92  
     93 int main(){
     94 #ifndef ONLINE_JUDGE
     95     freopen("2716.in","r",stdin);
     96     freopen("2716.out","w",stdout);
     97 #endif
     98     cnt=n=getint(); m=getint();
     99     F(i,1,n) t[i].read();
    100     root=build(1,n,1);
    101     F(i,1,m){
    102         int t=getint(); tmp.read();
    103         if (t==1) Insert(root,1);
    104         else{
    105             ans=INF;
    106             query(root);
    107             printf("%d
    ",ans);
    108         }
    109     }
    110     return 0;
    111 }
    View Code

    2648: SJY摆棋子

    Time Limit: 20 Sec  Memory Limit: 128 MB
    Submit: 1090  Solved: 359
    [Submit][Status][Discuss]

    Description

    这 天,SJY显得无聊。在家自己玩。在一个棋盘上,有N个黑色棋子。他每次要么放到棋盘上一个黑色棋子,要么放上一个白色棋子,如果是白色棋子,他会找出距 离这个白色棋子最近的黑色棋子。此处的距离是 曼哈顿距离 即(|x1-x2|+|y1-y2|) 。现在给出N<=500000个初始棋子。和M<=500000个操作。对于每个白色棋子,输出距离这个白色棋子最近的黑色棋子的距离。同一 个格子可能有多个棋子。
     

    Input

    第一行两个数 N M
    以后M行,每行3个数 t x y
    如果t=1 那么放下一个黑色棋子
    如果t=2 那么放下一个白色棋子

    Output

    对于每个T=2 输出一个最小距离
     

    Sample Input

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

    Sample Output


    1
    2

    HINT

     

    kdtree可以过

    Source

    [Submit][Status][Discuss]
  • 相关阅读:
    STA分析(四) lib model
    STA分析(三) cmos模型
    STA分析(二) multi_cycle and false
    STA分析(一) setup and hold
    UVM环境(一)
    Perl中的正则表达式(五)
    RVDS编译器
    ARM的Trust Zone技术
    001-shell基础,创建,运行
    006-mac下finder操作
  • 原文地址:https://www.cnblogs.com/Tunix/p/4514178.html
Copyright © 2011-2022 走看看