KD树kexinxin

KD树是一种查询索引结构,广泛应用于数据库索引中。从概念的角度讲,它是一种高纬数据的快速查询结构,本文首先介绍1维数据的索引查询,然后介绍2维KD树的创建和查询

2.1维数据的查询

平衡二叉树示意图

对于1维数据的查询,使用平衡二叉树建立索引即可。如果现在将查询条件变为:语文成绩介于30~93,数学成绩结余30~90,又该如何处理呢?

3.KD树

针对多维数据索引,是否也存在类似的一维的索引方法呢?先看2维数据的集合示意图:

2维数据示意图

如果先根据语文成绩,将所有人的成绩分成两半,其中一半的语文成绩<=c1,另一半的语文成绩>c1,分别得到集合S1,S2;然后针对S1,根据数学成绩分为两半,其中一半的数学成绩<=m1,另一半的数学成绩>m1,分别得到S3,S4,针对S2,根据数学成绩分为两半,其中一半的数学成绩<=m2,另一半的数学成绩>m2,分别得到S5,S6;再根据语文成绩分别对S3,S4,S5,S6继续执行类似划分得到更小的集合,然后再在更小的集合上根据数学成绩继续,...

上面描述的就是构建KD树的基本思路,其构建后的KD树如下图所示:

KD树示意图

如图所示,l1左边都是语文成绩低于45分,l1右边都是语文成绩高于45分的;l2下方都是语文成绩低于45分且数学成绩低于50分的,l2上方都是语文成绩低于45分且数学成绩高于50分的,后面以此类推。下面的图示,更清晰地表示了KD树的结构及其对应的二叉树:

KD树及对应的二叉树

在了解了KD树的基本原理后,剩下的工作就是如何构建KD树以及如何在KD树上查询了。

3.1KD树构建算法

相对而言,构建KD树是针对高维数据,需要针对每一维都进行二分,针对二维数据的KD树构建算法如下图所示:

KD树构建算法

其中的P表示待构建的元素集合,depth表示当前是KD树的第几层,如果depth是偶数,通过纵向线对集合进行划分;如果depth是奇数,通过横向线进行划分(3~5行);第6、7行递归进行KD树中子树的构建。

3.2KD树查询算法

在构建了KD树的基础上,如何进行查询其实是一个相对简单的问题了,在这里需要注意的是,在KD树中每一层划分所依据的是哪一维的数据,其它的根二叉树其实没有差别。KD树查询算法如下图所示:

查询算法

算法的v表示KD树中当前搜索的子树,R表示是一个高维数据的区域,区域的概念下图所示:

区域示意图

KD树查询递推公式

4.小结

1.2)寻找d维最小坐标值点a)若当前节点的切分维度是d因其右子树节点均大于等于当前节点在d维的坐标值,所以可以忽略其右子树,仅在其左子树进行搜索。若无左子树,当前节点即是最小坐标值节点。b)若当前节点的切分维度不是d需在其左子树与右子树分别进行递归搜索。如下为寻找d维最小坐标值点代码:

1.3)新增节点从根节点出发,若待插入节点在当前节点切分维度的坐标值小于当前节点在该维度的坐标值时,在其左子树插入;若大于等于当前节点在该维度的坐标值时,在其右子树插入。递归遍历,直至叶子节点。如下为新增节点代码:

多次新增节点可能引起树的不平衡。不平衡性超过某一阈值时,需进行再平衡。1.4)删除节点最简单的方法是将待删节点的所有子节点组成一个新的集合,然后对其进行重新构建。将构建好的子树挂载到被删节点即可。此方法性能不佳,下面考虑优化后的算法。假设待删节点T的切分维度为x,下面根据待删节点的几类不同情形进行考虑。a)无子树本身为叶子节点,直接删除。b)有右子树在T.right寻找x切分维度最小的节点p,然后替换被删节点T;递归处理删除节点p。c)无右子树有左子树在T.left寻找x切分维度最小的节点p,即p=findmin(T.left,cutting-dim=x),然后用节点p替换被删节点T;将原T.left作为p.right;递归处理删除节点p。(之所以未采用findmax(T.left,cutting-dim=x)节点来替换被删节点,是由于原被删节点的左子树节点存在x维度最大值相等的情形,这样就破坏了左子树在x分割维度的坐标需小于其根节点的定义)如下为删除节点代码:

2)最近邻搜索给定点p,查询数据集中与其距离最近点的过程即为最近邻搜索。如在上文构建好的k-dtree上搜索(3,5)的最近邻时,本文结合如下左右两图对二维空间的最近邻搜索过程作分析。a)首先从根节点(7,2)出发,将当前最近邻设为(7,2),对该k-dtree作深度优先遍历。以(3,5)为圆心,其到(7,2)的距离为半径画圆(多维空间为超球面),可以看出(8,1)右侧的区域与该圆不相交,所以(8,1)的右子树全部忽略。b)接着走到(7,2)左子树根节点(5,4),与原最近邻对比距离后,更新当前最近邻为(5,4)。以(3,5)为圆心,其到(5,4)的距离为半径画圆,发现(7,2)右侧的区域与该圆不相交,忽略该侧所有节点,这样(7,2)的整个右子树被标记为已忽略。c)遍历完(5,4)的左右叶子节点,发现与当前最优距离相等,不更新最近邻。所以(3,5)的最近邻为(5,4)。

如下为最近邻搜索代码:3)复杂度分析

操作

平均复杂度

最坏复杂度

新增节点

O(logn)

O(n)

删除节点

最近邻搜索

4)scikit-learn使用scikit-learn是一个实用的机器学习类库,其有KDTree的实现。如下例子为直观展示,仅构建了一个二维空间的k-dtree,然后对其作k近邻搜索及指定半径的范围搜索。多维空间的检索,调用方式与此例相差无多。

THE END
1.kdtree算法假设有6个二维数据点{(2,3),(5,4),(9,6),(4,7),(8,1),(7,2)},数据点位于二维空间内(如下图中黑点所示)。kd树算法就是要确定图1中这些分割空间的分割线(多维空间即为分割平面,一般为超平面)。下面就要通过一步步展示kd树是如何确定这些分割线的。 https://blog.csdn.net/weixin_43834466/article/details/127621740
2.一看就懂的K近邻算法(KNN),KD树,并实现手写数字识别!如上算法所述,kd树的构建是一个递归过程,我们对左子空间和右子空间内的数据重复根节点的过程就可以得到一级子节点(5,4)和(9,6),同时将空间和数据集进一步细分,如此往复直到空间中只包含一个数据点。 与此同时,经过对上面所示的空间划分之后,我们可以看出,点(7,2)可以为根结点,从根结点出发的两条红粗斜线指https://cloud.tencent.com/developer/article/1486641
3.KDTree原理和应用51CTO博客kd 树(k-dimensional tree)是一个包含空间信息的二项树数据结构,它是用来计算 kNN 的一个非常常用的工具。如果特征的维度是 D,样本的数量是N,那么一般来讲 kd 树算法的复杂度是O(D log(N)),相比于穷算的 O(DN) 省去了非常多的计算量。 1 构建KD树 https://blog.51cto.com/u_13267193/5949103
4.基于KD树的kmeans聚类算法优化聚类分析 k-means聚类 KD树 近似近邻https://www.cnki.com.cn/Article/CJFDTotal-DLXZ202111042.htm
5.基于KD树的SIFT特征点匹配算法.pdf第11卷 第2期 孙敏:基于 KD树的SIFT特征点匹配算法 2014年 6月 基于KD树的SIFT特征点匹配算法 孙敏 (烟台南山学院,山东烟台,265713) 摘要:增强现实领域中跟踪技术是一个很重要 的研 究课题 ,其中特征点的实时匹配是跟 踪算法的关键之一,而跟踪算法中传统的匹配方法复杂,对跟踪的实时性影响较大。为此,应 用尺https://max.book118.com/html/2017/0706/120709296.shtm
6.KD树的应用(3)BBF算法数据分析师KD树近邻搜索改进之BBF算法 原理在上文第二部分已经阐述明白,结合大顶堆找最近的K个近邻思想,相关主体代码如下: //KD树近邻搜索改进之BBF算法 intkdtree_bbf_knn(structkd_node* kd_root,structfeature* feat,intk, structfeature*** nbrs,intmax_nn_chks )//2 https://www.cda.cn/view/2069.html
7.KNN(K近邻)算法之——KDTree构建及查找原理本文主要讲解KNN算法中用于快速检索最近元素的KD树的构建及查找原理。 为了达到最佳阅读效果,请读者按照本文顺序阅读,文章使用了大量图片帮助读者理解。 1 背景 1.1 为什么要使用KD-Tree? k近邻法(KNN)最简单的实现方法是线性扫描。这时要计算输入实例与每一个训练实例的距离。当训练集很大时,计算非常耗时,这种方法是https://www.erlo.vip/share/40/107293.html
8.KD树的最近邻搜索算法数据分析师KD树的最近邻搜索算法_数据分析师 现实生活中有许多问题需要在多维数据的快速分析和快速搜索,对于这个问题最常用的方法是所谓的kd树。在k-d树中进行数据的查找也是特征匹配的重要环节,其目的是检索在k-d树中与查询点距离最近的数据点。在一个N维的笛卡儿空间在两个点之间的距离是由下述公式确定: https://cda.pinggu.org/view/2064.html
9.数据结构与算法kd二叉树(kNN)接下来探讨改进删除算法。删除算法的效率不高,原因在于需要不停的遍历被删除节点下的某颗子树,不仅耗费时间而且浪费计算资源。怎么改进呢? 有一种叫做替罪羊的算法可以用到这里。就是说,每次删除节点的时候,不是真正的删除,而是做个标记表明这个节点已删除,这样就不会影响kd树的平衡。但是被标记的节点太多也不好,怎么https://www.imooc.com/article/273871
10.Python实现KNN与KDTreeKD树 这是我见过写的最详细,最通俗易懂的KD树算法。 KD树构建与查询导图 学习KD树中的疑问: 需要预测的值若已经存在于KD树中,应该咋办? 在二分查找的过程中,记录下“走过”每一个节点时对应的距离。当遍历至叶子节点时,“重复点”一定被记录下来了。 https://www.jianshu.com/p/9a13fde6a1a3
11.复杂环境下肉牛三维点云重建与目标提取方法为从复杂环境中提取肉牛目标点云,本研究基于PCL点云库与C++语言开发了一套肉牛点云提取算法,包含点云滤波与点云抽稀、肉牛点云目标提取等两部分,最终实现复杂环境下肉牛三维点云目标提取,算法流程如图4所示。 图4 图4肉牛三维点云目标提取算法流程 Fig. 43D point cloud of beef cattle target extraction algorithmhttps://www.smartag.net.cn/article/2022/2096-8094/2096-8094-2022-4-2-64.shtml
12.matlab实现kdtree用matlab编写的关于Kd树算法,很实用的 上传者:weixin_42662293时间:2022-07-14 kd-tree算法 matlab matlab可用的kd-tree算法,运行时请将mex下对应系统的文件加入到matlab路径中 上传者:fyy8586时间:2010-04-20 kdtree_in_matlab_kd树聚类_ 一种用于求解振动问题非线性微分方程的计算方法。一般来说,求解振动问题微分https://www.iteye.com/resource/wjx2040-3736796
13.pythonK近邻算法的kd树实现python这篇文章主要介绍了python K近邻算法的kd树实现,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧 k近邻算法的介绍 k近邻算法是一种基本的分类和回归方法,这里只实现分类的k近邻算法。 k近邻算法的输入为实例的特征向量,对应特征空间的点;输出为实例的类别,可以取多类。 https://www.jb51.net/article/146976.htm