zoukankan      html  css  js  c++  java
  • 「学习笔记」KD Tree

    KD-Tree

    个人感觉 ( m{KD-Tree}) 在操作的时候是要分割每一维的空间的

    就是按照某种方式把空间分割了,常见的有选中位数和方差来敲定是哪一维的

    然后在操作的时候在分割后的每个区域内部进行查询,不符合的区域不会进行查询

    (暴搜+剪枝的本质展露了)


    信息

    每个节点要维护的东西

    (fa,ls,rs,) 父亲,左右儿子

    (pos) 这个点储存的真实点和分割的坐标轴

    (mn,mx) 表示几个维度内部当前维的最大最小值

    (可以拿来剪枝)

    这里:树上的每个节点储存的真实节点的顺序是不一定一样的,分割坐标轴那个变量可能存在相同的

    然后同时这里还可以维护子树的一些信息

    比如点权极值或者和,子树大小(范围内部点的个数)


    建树

    对于每个 ([l,r]) 选择区间内部方差最大的维度然后 (split)

    这里找方差就是纯粹模拟套公式

    (mid) 和线段树一样,然后递归就成的了


    查询

    本质上就是个暴搜+剪枝

    以求解最近最远距离举例

    如果要求最近距离,那么枚举 (n) 个点在树上面查询

    (算了查询具体去看代码吧,代码极为易懂)

    注意如果当前维度的差小于距离,那么意味着另一个儿子也有可能是答案,也得去查询

    一般会考虑搞一个估价函数之类的

    同时对于答案的记忆化也是常见的操作,比如比当前答案劣就不再查询子树内信息之类的

    还有一些基础操作,依题而来

    判断k维包含关系,有交集关系,点在空间外的关系

    用在矩形框点里面的

    (这三个全都是模拟就能得到的)


    修改

    (先说权值问题)

    单点的,直接找到那个点,然后改,(push\_up) 啥的一样做

    范围内的,跟线段树一样,找到是不是范围包含,然后标记永久化来一波

    如果没交集直接退,有部分交,那么递归

    插入

    啊这个要用上替罪羊的思想啦,如果有个子树超过平衡因子 (alpha),那么暴力重构它就好了

    先回收,再 (build)


    这个空间复杂度好像是个 (O(n)) 的,但是时间复杂度就比较玄学,好像还很容易卡 (dots)

    例题

    Luogu3769 [CH弱省胡策R2]TATT

    (sort) 第一维,降下来一维

    [f_{i}=maxlimits_{j=1}^{i-1} [f_j+1](b_jge b_i,c_jge c_i,d_jge d_i) ]

    所以后面是个三维偏序,然后上 (K-D Tree)

    支持插入一个新点,空间内查询最大值

    卡常的话可以先把所有点都建出来

  • 相关阅读:
    PyQt 滚动条自动到最底部
    Python 装饰器示例,计算函数或方法执行时间
    pyuic5将.ui文件转为.py文件
    Python pyinstaller 参数
    Win+R 常用命令
    CODEVS 2171 棋盘覆盖
    P3924 康娜的线段树
    P1850 换教室
    U33405 纽约
    POJ
  • 原文地址:https://www.cnblogs.com/yspm/p/13435326.html
Copyright © 2011-2022 走看看