zoukankan      html  css  js  c++  java
  • k-d树模板(BZOJ2648)

    实现了插入一个点,查询距某个位置的最近点。

    #include <cstdio>
    #include <algorithm>
    using namespace std;
    
    const int N = 500005, inf = 0x3f3f3f3f;
    int n,q,D,rt,op,ans,b[2];
    struct nd {
        int l,r,d[2],mn[2],mx[2];
        bool operator < (const nd &b) const {return d[D] < b.d[D];}
    }t[N<<1];
    int rd() {
        int r = 0, f = 1, c = getchar();
        while(c < '0' || c > '9') {if(c == '-') f = -1; c = getchar();}
        while(c >= '0' && c <= '9') r = r*10+c-'0', c = getchar();
        return r*f;
    }
    
    void pu(int x) {
        for(int i = 0; i < 2; i++) {
            t[x].mn[i] = min(t[x].mn[i],min(t[t[x].l].mn[i],t[t[x].r].mn[i]));
            t[x].mx[i] = max(t[x].mx[i],max(t[t[x].l].mx[i],t[t[x].r].mx[i]));
        }
    }
    int bd(int l, int r, int d) {
        if(l > r) return 0;
        int m = (l+r)>>1;
        D = d, nth_element(t+l, t+m, t+r+1);
        for(int i = 0; i < 2; i++) t[m].mn[i] = t[m].mx[i] = t[m].d[i];
        t[m].l = bd(l, m-1, d^1), t[m].r = bd(m+1, r, d^1), pu(m);
        return m;
    }
    void in(int o, int d) {
        if(b[d] >= t[o].d[d]) {
            if(t[o].r) in(t[o].r, d^1);
            else {
                t[o].r = ++n;
                for(int i = 0; i < 2; i++) t[n].mn[i] = t[n].mx[i] = t[n].d[i] = b[i];
            }
        } else {
            if(t[o].l) in(t[o].l, d^1);
            else {
                t[o].l = ++n;
                for(int i = 0; i < 2; i++) t[n].mn[i] = t[n].mx[i] = t[n].d[i] = b[i];
            }
        }
        pu(o);
    }
    int gt(int o, int x, int y) {
        return max(0,t[o].mn[0]-x)+max(0,t[o].mn[1]-y)+max(0,x-t[o].mx[0])+max(0,y-t[o].mx[1]);
    }
    void qry(int o, int x, int y) {
        int ds = abs(t[o].d[0]-x)+abs(t[o].d[1]-y), dl = gt(t[o].l,x,y), dr = gt(t[o].r,x,y);
        ans = min(ans, ds);
        if(!t[o].l) dl = inf; if(!t[o].r) dr = inf;
        if(dl < dr) {
            if(dl < ans) qry(t[o].l,x,y);
            if(dr < ans) qry(t[o].r,x,y);
        } else {
            if(dr < ans) qry(t[o].r,x,y);
            if(dl < ans) qry(t[o].l,x,y);
        }
    }
    
    int main() {
        n = rd(), q = rd();
        for(int i = 1; i <= n; i++) t[i].d[0] = rd(), t[i].d[1] = rd();
        t[0].mn[0] = t[0].mn[1] = inf, t[0].mx[0] = t[0].mx[1] = -inf, rt = bd(1, n, 0);
        while(q--) {
            op = rd(), b[0] = rd(), b[1] = rd();
            if(op^1) ans = inf, qry(rt,b[0],b[1]), printf("%d
    ", ans); else in(rt,0);
        }
        return 0;
    }
  • 相关阅读:
    boost::asio 连接管理11 如何关闭连接
    boost::asio async_write也不能保证一次发完所有数据 二
    boost::asio async_write也不能保证一次发完所有数据 一
    boost参考博客
    C++ 多线程编程总结
    Boost::asio io_service 实现分析
    使用boost io_service时,需要注意的东西
    Boost::Thread 多线程的基础知识
    boost::thread类
    Boost::thread库的使用
  • 原文地址:https://www.cnblogs.com/juruolty/p/6209939.html
Copyright © 2011-2022 走看看