【问题标题】:How to find if a point exists in which polygon如何查找一个点是否存在于哪个多边形中
【发布时间】:2012-06-02 05:13:06
【问题描述】:

如何找到一个点是否存在于给定的一组多边形中? 我有像

这样的坐标
polygonA = 1(0,0),2(0,5),3(3,4),4(3,5),5( 2,2)
polygonB = 1(10,10),2(10,15),3(13,14),4(13,15),5(12,12)

我有一个点,因为 (6,4) 现在想搜索这个点是否在这个多边形中的任何一个中,或者两者都在,或者离哪个多边形最近。

如何存储这些数据(多边形)?有系统/数据库/算法来做这个搜索吗?

更新:感谢大家这么快的反应...我想我需要更具体...

如何搜索 = 是的...得到了 algorithmslibrary 的列表。

如何存储 = 基于我的研究 SQL 和 NoSQL db 有它们的解决方案。 NoSQL = MongoDb 似乎最接近我所需要的。但问题是我可以像 "db.places.find({ "loc" : { "$within" : { "$polygon" : polygonB } } })" 那样查询但不能像 db.places.find({ " loc" : { "$within" : { } } }) SQL 检查了 postgre 和 openGIS 以获得一些帮助。但是 colud 不知道它是否可能。

如果有人可以帮助我...在此先感谢。

【问题讨论】:

  • 你的多边形是凸的、凹的、自相交的吗?
  • 另见answer
  • @nhahtdh,有什么关系?
  • @Beta - 某些算法效率低下或不适用于某些类型的多边形。这就是为什么它很重要。但是,有些算法涵盖了所有情况(如果我没记错的话),但不如特殊情况算法快。

标签: java postgresql mongodb geometry opengis


【解决方案1】:

基本方法(如果您有少量多边形)是将所有多边形存储在一个集合中并循环遍历元素以检查一个点是否在多边形内。

另一方面,如果你有大量的多边形,我会推荐使用标准库中没有的 R-tree 数据结构。如果你想使用 R-tree 选项,你应该检查这个项目:http://sourceforge.net/projects/jsi/

R-tree 允许您索引矩形(在这种情况下为多边形的边界框)。因此,您可以使用 R-tree 非常快速地找到少量候选多边形。然后你可以遍历候选列表得到最终结果。

【讨论】:

  • 我认为更重要的是如何检查一个点是否在特定的多边形中,而不是如何缩放算法。
  • 我不太确定,因为 java.awt.Polygon 已经有许多 contains() 方法可以做到这一点。无论如何,从问题上看并不那么明显,所以你也可以是对的。
  • 您好 vizier 感谢您的帮助。是的,我需要如何查找和如何存储,但也要高效。在查看不同的结构时,我发现 MongoDB 最接近我需要的结构。 mongoDB的问题是我不能像“从poly_table中选择poly_table中的点(x,y)”这样的查询......根据mongo描述我可以说“”db.places.find({“loc”:{“$within " : { "$polygon" : polygonB } } }) ""...谁能帮帮我(更新问题)
  • 你也应该检查这个问题(如果还没有):stackoverflow.com/questions/2041622/nosql-and-spatial-data
【解决方案2】:

您可以使用 GeneralPath 类来帮助您确定如果点与多边形相交。首先,创建一个添加了坐标的 GeneralPath:

    GeneralPath gp = new GeneralPath();
    double[] x = ...
    double[] y = ...
    gp.moveTo(x[0], y[0]);
    for (int i =1; i < x.length; i++) {
        gp.lineTo(x[i], y[i]);
    }
    gp.closePath();

    if (gp.contains(pointX, pointY)) {
        ...
    }

对于一个点更接近哪个多边形的问题,这在一定程度上取决于您需要解决方案的准确程度。

为了获得准确的解决方案,这相当于(未经优化):

  • 取点与连接每个多边形顶点的每条线(线段)之间的最短距离(Java2D 显然没有为此提供方法,但点到线的最短距离是fairly simple calculation)
  • 哪个多边形的直线到该点的距离最短?

在实践中,您可以为某些应用程序近似此过程。例如,您可以更有效地执行以下操作:

  • 取每个多边形的边界矩形的中心点(GeneralPath.getBounds() 会给你这个)
  • 获取查询点与每个中心点之间的距离,看看哪个最近。

如果您确实需要一个准确的答案,那么您可以结合这些技术来优化您在所有顶点中的搜索。例如,您可以按到“中心点”(如上定义)的距离对多边形进行排序。从最小到最大距离搜索。如果到目前为止您找到的线段的最小距离是 d,那么您可以自动排除从查询点到其“中心点”的距离为 d + r 的任何多边形 P,其中 r 是长度的一半P 的边界矩形的对角线(换句话说,为简单起见,您可以想象围绕该边界框的边界圆,并检查到该边界圆的距离是否比目前在其他多边形上找到的最近点更远)。

我不太了解数据库。您的多边形只是定义为一系列点。您决定如何将这些存储在内存/文件中对算法本质上没有任何影响。

【讨论】:

  • 精确解部分有点奇怪。我认为方法应该是:你必须计算到线段的最短距离,其中你必须为多边形的每个线段计算一次到线的距离和两次到点的距离。对于自相交多边形的情况,这可能有点不明确。
  • 我不确定我是否理解。我基本上是在说:“将点到多边形的距离视为到最近顶点的距离”。你把它当作别的东西吗?
  • P.S.我忽略了自相交多边形的情况。
  • 我认为从点到多边形的最短距离是从点到连接定义多边形的顶点的所有线段的最短距离,而不是到的最短距离顶点单独。
  • 抱歉,我知道现在发生了什么——我们以相同的方式定义它,但我混淆了我的术语。 “顶点”是指“连接顶点的线/段”(例如,我提到了计算点到线距离的算法)。很抱歉混淆了 - 已在上面更正。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-09-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-11-21
  • 1970-01-01
相关资源
最近更新 更多