1. 程式人生 > >bzoj2648: SJY擺棋子

bzoj2648: SJY擺棋子

+= esp names get insert cmp date 重構 !=

本機ac的重構kdtree沒有不重構快???bzoj鬼機

#include<cstdio>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<algorithm>
#include<cmath>
using namespace std;
int read()
{
    int x=0,f=1;char ch=getchar();
    while(ch<0||ch>9){if(ch==-)f=-1
;ch=getchar();} while(0<=ch&&ch<=9){x=x*10+ch-0;ch=getchar();} return x*f; } int u[2]; struct KDtree { int lc,rc,p[2],mn[2],mx[2]; }tr[1100000];int trlen,rt; void add() { int now=++trlen; tr[now].p[0]=tr[now].mn[0]=tr[now].mx[0]=u[0]; tr[now].p[1]=tr[now].mn[1
]=tr[now].mx[1]=u[1]; } void insert() { add(); if(rt==0){rt=trlen;return ;} int now=rt,w=0; while(1) { tr[now].mn[0]=min(tr[now].mn[0],tr[trlen].mn[0]); tr[now].mx[0]=max(tr[now].mx[0],tr[trlen].mx[0]); tr[now].mn[1]=min(tr[now].mn[1],tr[trlen].mn[1]); tr[now].mx[
1]=max(tr[now].mx[1],tr[trlen].mx[1]); if(tr[trlen].p[w]<tr[now].p[w]) { if(tr[now].lc==0){tr[now].lc=trlen;return ;} else now=tr[now].lc; } else { if(tr[now].rc==0){tr[now].rc=trlen;return ;} else now=tr[now].rc; } w^=1; } } //~~~~~~~~~~~~~~~~~~~~~~~~~~insert~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ int cw;bool cmp(KDtree t1,KDtree t2){return t1.p[cw]==t2.p[cw]?t1.p[cw^1]<t2.p[cw^1]:t1.p[cw]<t2.p[cw];} void clear(int now) { tr[now].lc=tr[now].rc=0; tr[now].mn[0]=tr[now].mx[0]=tr[now].p[0]; tr[now].mn[1]=tr[now].mx[1]=tr[now].p[1]; } void update(int now) { int lc=tr[now].lc,rc=tr[now].rc; for(int i=0;i<=1;i++) { if(lc!=0) { tr[now].mn[i]=min(tr[now].mn[i],tr[lc].mn[i]); tr[now].mx[i]=max(tr[now].mx[i],tr[lc].mx[i]); } if(rc!=0) { tr[now].mn[i]=min(tr[now].mn[i],tr[rc].mn[i]); tr[now].mx[i]=max(tr[now].mx[i],tr[rc].mx[i]); } } } int rebuild(int l,int r,int w) { int mid=(l+r)/2; cw=w;nth_element(tr+l,tr+mid,tr+r+1,cmp); clear(mid); if(l<mid)tr[mid].lc=rebuild(l,mid-1,w^1); if(mid<r)tr[mid].rc=rebuild(mid+1,r,w^1); update(mid); return mid; } //~~~~~~~~~~~~~~~~~~~~~~~~~rebuild~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ int ans; int getdis(int now) { if(now==0)return 2147483647; int ret=0; for(int i=0;i<=1;i++) { if(u[i]<tr[now].mn[i])ret+=tr[now].mn[i]-u[i]; if(tr[now].mx[i]<u[i])ret+=u[i]-tr[now].mx[i]; } return ret; } void findans(int now,int w) { ans=min(ans,abs(u[0]-tr[now].p[0])+abs(u[1]-tr[now].p[1])); int lc=tr[now].lc,rc=tr[now].rc; int dl=getdis(lc),dr=getdis(rc); if(dl<dr) { if(dl<ans)findans(lc,w^1); if(dr<ans)findans(rc,w^1); } else { if(dr<ans)findans(rc,w^1); if(dl<ans)findans(lc,w^1); } } //~~~~~~~~~~~~~~~~~~~~~~~~findans~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ int main() { freopen("a.in","r",stdin); freopen("a.out","w",stdout); int n,Q,op; n=read(),Q=read(); trlen=0,rt=0; for(int i=1;i<=n;i++) u[0]=read(),u[1]=read(),add(); rt=rebuild(1,trlen,0); while(Q--) { op=read(),u[0]=read(),u[1]=read(); if(op==1) { insert(); //if(trlen%100000==0)rt=rebuild(1,trlen,0); } else { ans=2147483647; findans(rt,0); printf("%d\n",ans); } } return 0; }

bzoj2648: SJY擺棋子