Python:多边形中的点、边界和顶点检查(光线投射)
因此,我编写了一些代码来检查点[(x,y)]是否位于多边形[(x,y),(x,y),(x,y),(x,y)]内,但是如果该点位于边界或顶点上,代码将失败,我需要将其归类为位于多边形内。代码如下:Python:多边形中的点、边界和顶点检查(光线投射),python,polygon,spatial,point,raycasting,Python,Polygon,Spatial,Point,Raycasting,因此,我编写了一些代码来检查点[(x,y)]是否位于多边形[(x,y),(x,y),(x,y),(x,y)]内,但是如果该点位于边界或顶点上,代码将失败,我需要将其归类为位于多边形内。代码如下: def areasign(poly): sumarea = 0 for i in range(0, len(poly)-1): xi = poly[i][0] yi = poly[i][1] xj = poly[i+1][0]
def areasign(poly):
sumarea = 0
for i in range(0, len(poly)-1):
xi = poly[i][0]
yi = poly[i][1]
xj = poly[i+1][0]
yj = poly[i+1][1]
sumarea = sumarea + ((xi*yj)-(yi*xj))
if sumarea == 0: return 0
if sumarea < 0: return -1
if sumarea > 0: return 1
def lineintersection(xy, ij):
xyi = []
xyj = []
ijx = []
ijy = []
xyi.extend(xy)
xyj.extend(xy)
xyi.append(ij[0])
xyj.append(ij[1])
xyi.append(xy[0])
xyj.append(xy[0])
ijx.extend(ij)
ijy.extend(ij)
ijx.append(xy[0])
ijy.append(xy[1])
ijx.append(ij[0])
ijy.append(ij[0])
a = areasign(xyi)
b = areasign(xyj)
c = areasign(ijx)
d = areasign(ijy)
if (a!= b) and (c!=d):
return True
else:
return False
def openpointfile(fname):
p = []
f = open(fname)
for line in f:
line = line.replace('POINT(', '')
line = line.replace(')', '')
vals = line.split(' ')
res = map(float, vals)
ctuple = tuple(res)
p.append(ctuple)
print ctuple
f.close()
return p
points = openpointfile('C:/Users/Dan/Documents/Informatics/Data/Point_On_Line.txt')
def openpolygonfile(fname):
p = []
f = open(fname)
for line in f:
line = line.replace('POLYGON((', '')
line = line.replace('))', '')
s = line.split(',')
poly = []
for coord in s:
vals = coord.split(' ')
res = map(float, vals)
ctuple = tuple(res)
poly.append(ctuple)
p.append(poly)
f.close()
return p
polys = openpolygonfile('C:/Users/Dan/Documents/Informatics/Data/Polygon_On_Line.txt')
def pointinpoly(points, polys):
infinity = tuple([100000000.0, 100000010.0])
sum = 0
testline = (points, infinity)
for i in range(0, len(poly)-1):
start = poly[i]
end = poly[i+1]
line = (start, end)
l = lineintersection(line, testline)
if l == True:
sum = sum + 1
if sum % 2 == 0:
return False
else:
return True
pointcount = 0
for point in points:
pointcount = pointcount + 1
polycount = 0
for poly in polys:
polycount = polycount + 1
l = pointinpoly(point, poly)
res = 'Point ' + str(pointcount) + ' lies within Polygon ' + str(polycount) + ' = ' + str(l)
print l
print (res)
def区域标志(多边形):
面积=0
对于范围(0,len(poly)-1)内的i:
席=聚[i]〔0〕
yi=poly[i][1]
xj=poly[i+1][0]
yj=poly[i+1][1]
sumarea=sumarea+((xi*yj)-(yi*xj))
如果sumarea==0:返回0
如果面积小于0:返回-1
如果sumarea>0:返回1
def测线交点(xy,ij):
xyi=[]
xyj=[]
ijx=[]
ijy=[]
扩展(xy)
扩展(xy)
xyi.append(ij[0])
xyj.append(ij[1])
附加(xy[0])
附加(xy[0])
ijx.extend(ij)
扩展(ij)
ijx.append(xy[0])
ijy.append(xy[1])
ijx.append(ij[0])
ijy.append(ij[0])
a=区域符号(xyi)
b=区域标志(xyj)
c=区域标志(ijx)
d=区域标志(ijy)
如果(a!=b)和(c!=d):
返回真值
其他:
返回错误
def openpointfile(fname):
p=[]
f=打开(fname)
对于f中的行:
直线=直线。替换('点(','')
行=行。替换('),“”)
VAL=行分割(“”)
res=映射(浮点,VAL)
ctuple=元组(res)
p、 附加(ctuple)
印刷品
f、 关闭()
返回p
points=openpointfile('C:/Users/Dan/Documents/Informatics/Data/Point\u On\u Line.txt')
def OpenPolyConfigure(fname):
p=[]
f=打开(fname)
对于f中的行:
直线=直线。替换('多边形((','')
行=行。替换('),“”)
s=行。拆分(',')
多边形=[]
对于s中的coord:
VAL=坐标拆分(“”)
res=映射(浮点,VAL)
ctuple=元组(res)
多边形附加(ctuple)
p、 附加(多边形)
f、 关闭()
返回p
polys=openpolyConfigure('C:/Users/Dan/Documents/Informatics/Data/Polygon\u On\u Line.txt')
def pointinpoly(点、多边形):
无穷大=元组([100000000.00100000010.0])
总和=0
测试线=(点,无穷大)
对于范围(0,len(poly)-1)内的i:
开始=多边形[i]
结束=多边形[i+1]
行=(开始、结束)
l=直线交点(直线、测线)
如果l==真:
总和=总和+1
如果总和%2==0:
返回错误
其他:
返回真值
点计数=0
对于点到点:
点计数=点计数+1
多计数=0
对于多边形中的多边形:
多计数=多计数+1
l=点多边形(点,多边形)
res='Point'+str(pointcount)+'位于多边形'+str(polycount)+'='+str(l)内
打印l
打印(res)
就像我之前说的,如果点位于边界或顶点上,这不起作用,我在这里找到了一个函数,它似乎起作用,但我找不到一种方法来将我的文件转换为函数的正确格式,并使它在多边形列表上迭代
def point_in_poly(x,y,poly):
# check if point is a vertex
if (x,y) in poly: return "IN"
# check if point is on a boundary
for i in range(len(poly)):
p1 = None
p2 = None
if i==0:
p1 = poly[0]
p2 = poly[1]
else:
p1 = poly[i-1]
p2 = poly[i]
if p1[1] == p2[1] and p1[1] == y and x > min(p1[0], p2[0]) and x < max(p1[0], p2[0]):
return "IN"
n = len(poly)
inside = False
p1x,p1y = poly[0]
for i in range(n+1):
p2x,p2y = poly[i % n]
if y > min(p1y,p2y):
if y <= max(p1y,p2y):
if x <= max(p1x,p2x):
if p1y != p2y:
xints = (y-p1y)*(p2x-p1x)/(p2y-p1y)+p1x
if p1x == p2x or x <= xints:
inside = not inside
p1x,p1y = p2x,p2y
if inside: return "IN"
else: return "OUT"
def point_in_poly(x,y,poly):
#检查点是否为顶点
如果多边形中有(x,y):返回“in”
#检查点是否位于边界上
对于范围内的i(len(poly)):
p1=无
p2=无
如果i==0:
p1=多边形[0]
p2=多边形[1]
其他:
p1=多边形[i-1]
p2=多边形[i]
如果p1[1]==p2[1]和p1[1]==y和x>min(p1[0],p2[0])和xmin(p1y,p2y):
如果你能把它安装得匀称些的话?有了它,就可以很容易地创建多段线和点集合,以查看单个点是否与它们中的任何一个相接触。如果事实上,使用shapely,我认为您甚至不需要担心边缘情况。对于我的一个项目,不幸的是,我们不允许使用shapely,因为我们需要使用它来测试它。我曾想过使用matplotlib和路径,但在看了6个小时后,我的头脑爆炸了,这也行。看看我在github上的pygridgen库,我有一个函数,它使用matplotlib来测试多边形中的点。不过,我不确定它是如何处理边界点的。谢谢您的回复!我现在要看一看:)你能安装得匀称吗?有了它,就可以很容易地创建多段线和点集合,以查看单个点是否与它们中的任何一个相接触。如果事实上,使用shapely,我认为您甚至不需要担心边缘情况。对于我的一个项目,不幸的是,我们不允许使用shapely,因为我们需要使用它来测试它。我曾想过使用matplotlib和路径,但在看了6个小时后,我的头脑爆炸了,这也行。看看我在github上的pygridgen库,我有一个函数,它使用matplotlib来测试多边形中的点。不过,我不确定它是如何处理边界点的。谢谢您的回复!我现在来看看:)