如何使用2D无限线作为可通过接近度查询的关联容器的键?

问题描述

我有数千条线段,希望通过共线性进行聚类。一种方法是用一个无限行的键创建一个关联容器。有了这样的容器,我可以使用线段的集合作为值,并通过确定该线段的无限线并将其插入相应的bin中来添加线段。

给出这样的设置,表征无限行的最佳方法是什么,以支持查询给定行附近的行键的数据结构的能力?

例如,我正在考虑使用点的R树(在该项目的其他地方,我已经在使用Boost.Geometry R树),其中每个点都是无限线的x轴截距和y轴截距。但是,这仅适用于非垂直和非水平线。我可以将垂直线和水平线作为特殊情况进行处理,但是那样我将无法轻松查询垂直线或水平线附近的线,而无法查询非轴线附近的线。通过对R树中的拦截点进行二维范围查询来对齐直线。

我想知道是否有一些优雅的方法可以解决此问题。如何将无限的2D线表示为点,以使水平线和垂直线与任何其他种类的线都没有不同,并且彼此靠近的线映射到彼此靠近的点?

解决方法

我有两种解决方法。 第一个是简单的,但有一些限制:

对于每条无限线,您可以计算直线上从原点绘制的垂直线与直线相交的点。您可以将该点的坐标存储为该线的“签名”。该解决方案将适用于除通过原点的线以外的所有线。那是因为当直线穿过原点时,无论直线的坡度如何,“签名”点将始终是原点。

第二个解决方案扩展了第一个解决方案,以解决该问题: 除上述点的坐标外,您还可以存储直线法线与x轴所成的角度。因此,您将用有序三元组(x,y,theta)表示每一行。您可以将这些三胞胎存储在3d点的rtree中,并查询该树。

穿过原点的两条线的theta值分别为pi / 4弧度和5 * pi / 4。它们会是巧合的,但是它们在rtree中的存储方式并不能反映这一点。因此,仅对于穿过原点的线,您可以强制执行约定,例如-theta必须介于0和pi之间。这样的约定将解决该问题。仅对穿过原点的线强制执行此约定。

更新:

要找到一个针对您的用例进行了更好优化的解决方案,将需要对如何测量两条无限行之间的“接近度”进行明确定义。

相关问答

错误1:Request method ‘DELETE‘ not supported 错误还原:...
错误1:启动docker镜像时报错:Error response from daemon:...
错误1:private field ‘xxx‘ is never assigned 按Alt...
报错如下,通过源不能下载,最后警告pip需升级版本 Requirem...