我们正在研究一种地图解决方案。 这里用户在地图上绘制了一个多边形,对于给定的点,我们需要找到点是否位于多边形内或外。
我们正在使用http://www.sql-statements.com/point-in-polygon.html之前的一种SQL技术来执行此任务,但在此期间我们发现它在某些区域不起作用。
有没有人对此有正确的解决方案?如果C#工作正常,我们也可以在C#中尝试解决方案
谢谢。
答案 0 :(得分:4)
如果您使用的是SQL Server 2008,则可以使用STIntersection (geography Data Type) - SQL Server将为您完成所有操作。
在这种情况下,我建议使用SQL Server 2008,因为它提供了对地理数据的本机支持。在使用它之前,“STIntersect giving incorrect result for geography Datatype”可能值得一读。该网站的示例:
declare @point geometry
declare @polygon geometry
set @point = geometry::STGeomFromText('POINT (-88.22 41.50000001)', 4326)
set @polygon = geometry::STGeomFromText('POLYGON ((-88.2 41.5, -88.2 41.6, -88.3 41.6, -88.3 41.5, -88.2 41.5))', 4326)--124
Select @point.STIntersection(@polygon).ToString()
答案 1 :(得分:1)
从http://en.wikipedia.org/wiki/Point_in_polygon
转述最简单的方法是从一个方向画一条想象线,并计算它穿过的线数。如果它是奇数,则该点在内部,即使该点在外面。
基本上遍历每个点对,找到它在你的点处穿过水平线的位置,如果它穿过右边,增加计数器,如果它向左交叉或者根本不交叉,则忽略它。在你的点上的水平线也不应该被计算(边界条件)。
答案 2 :(得分:1)
点P(x,y)是你的观点。点P0(x0,y0)和P1(x1,y1)形成一条线。我们绘制的虚线是为了看到我们穿过多少个多边形线是水平的。
1)首先确定哪些线实际上是可交叉的(与您绘制的虚线平行的线条或者线条上方或下方的线条显然不会交叉):
For each line of the polygon, compute weather P would be able to cross it.
If ((x0 < x < x1) OR (x0 > x > x1)) add line to some list.
2)确定哪些剩余行(列表中的行)实际交叉:
For each line in list, compute
result = (y - y0) * (x1- x0) - (x - x0) * (y1 - y0)
If (result < 0) the line was crossed, increment a counter.
If (result == 0) the point is ON the line, increment a counter if thats supposed
to count as the point having crossed the line, else don't ...
If (result > 0) the line was not crossed, so just continue with the loop.
[Note: double check weather I got the sides right ...]
3)现在,如果计数器是一个奇数,你的点在里面,如果它是偶数或零,它就在多边形之外。