将多边形与最近的相邻线连接以创建可切割的模板



我的Python脚本使用"connector lines"连接单独的多边形。基于最近邻算法,所以我可以把它们切成一个形状,像这样连接的多边形。

这很好,但我有三个问题:

  • 这些线实际上是而不是多边形之间最紧密的连接。为什么算法找不到红线(手动插入),但错误的黑线?看这里:错误的最近邻线-最近点函数是否可能只连接到节点而不连接到多边形线上的点?这就能解释抵消了吗?
  • 为了创建一个不太"摇摆"的稳定模板,我想添加额外的连接线。显然,我们需要一个非常不同的算法。我如何定义"不稳定",找到这些连接的标准是什么,这些连接会使模板更稳定?我认为答案在于找到多边形点之间的最短路径,然后将最短路径的长度与直线连接的长度进行比较。然后,我将添加以下连接:a)通过直行缩短路径的百分比最高;b)在总"节省"方面超过阈值。这必须迭代完成,因为新连接将改变所有其他路径的计算。我发现了一些有趣但复杂的算法来解决问题的第一部分:在一个多边形内找到最短路径:
  • https://pdfs.semanticscholar.org/d59f/b891cac975a3b1d627e6e096916e35235ff2.pdf
  • https://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.100.1319&代表= rep1& type = pdf
  1. 一个更简单的问题:用三个多边形创建地理数据框架的脚本部分似乎非常复杂。我相信有更简单的方法来做这件事。
import osmnx as ox
import matplotlib.pyplot as plt
import geopandas as gpd
from shapely.geometry import Point, Polygon, LineString
from shapely.ops import nearest_points
box=(51.4616,51.4522, -0.1354, -0.1628)
p1lat=[51.4596626, 51.4580315, 51.4579446, 51.4589807, 51.4599099, 51.4595690, 51.4587935, 51.4578643, 51.4577373, 51.4590141, 51.4603845, 51.4603578, 51.4596626]
p1long=[-0.1544094,-0.1543021,-0.1536155,-0.1533473,-0.1532292,-0.1521242,-0.1519632,-0.1526713,-0.1520705,-0.1510084,-0.1519740,-0.1538301,-0.1544094]
p1=Polygon(zip(p1long,p1lat))
p2lat=[51.4582654, 51.4572092, 51.4566744, 51.4562599, 51.4561930, 51.4569953, 51.4585930, 51.4594553, 51.4594553, 51.4580983, 51.4569084, 51.4567813, 51.4569552, 51.4571758, 51.4579379, 51.4581652, 51.4582989, 51.4585796, 51.4587601, 51.4582654]
p2long=[-0.1493561,-0.1497531,-0.1492059,-0.1475108,-0.1460624,-0.1456332,-0.1454616,-0.1456439,-0.1460516,-0.1460302,-0.1463413,-0.1471460,-0.1477575,-0.1486588,-0.1486266,-0.1473176,-0.1467168,-0.1466846,-0.1468456,-0.1493561,]
p2=Polygon(zip(p2long,p2lat))
p3lat=[51.4608859, 51.4608424, 51.4604213, 51.4600904, 51.4600235, 51.4602241, 51.4603110, 51.4606385, 51.4606185, 51.4608859]
p3long=[-0.1481116,-0.1507562,-0.1511103,-0.1510674,-0.1480097,-0.1480311,-0.1504290,-0.1504987, -0.1480740,-0.1481116]
p3=Polygon(zip(p3long,p3lat))
polygons = gpd.GeoDataFrame(index=[0], geometry=[p1])
polygons=polygons.append(gpd.GeoDataFrame(index=[0], geometry=[p2]))
polygons=polygons.append(gpd.GeoDataFrame(index=[0], geometry=[p3]))
polygons.set_crs(epsg=4326, inplace=True)
def createcard(layer,lcolor, framewidth, connectorwidth):
dflines = gpd.GeoDataFrame(columns=['ID','Location','geometry']) #connector lines
dfframes =gpd.GeoDataFrame(columns=['ID','Location','geometry']) #frames
df=layer
df=df.dissolve().explode()
df.insert(1,'nearest_geometry', None)
df.insert(2,'queried_geometry', None)
while df.shape[0]>1: #add connector lines to the dataframe, explode and dissolve until therev is only 1 polygon, i.e. everything is connected
for index, row in df.iterrows():
point = row.geometry
multipoint = df.drop(index, axis=0).geometry.unary_union
queried_geom, nearest_geom = nearest_points(point, multipoint)
df.loc[index, 'nearest_geometry'] = nearest_geom
df.loc[index, 'queried_geometry'] = queried_geom
x=LineString([nearest_geom,queried_geom]).buffer(connectorwidth)
dflines=dflines.append({'geometry' : x, 'ID':'2','Location':'test'},ignore_index=True)
df=df.append(dflines).dissolve().explode() # add the connector lines to the df and make it one polygon 
fig, ax = plt.subplots(figsize=(15,15))
ox.plot.plot_footprints(df, ax=ax, bbox=box ,  color=lcolor, alpha=1, bgcolor='#FFFF', save=True, show=False, close=False)

Google Colab笔记本的代码:https://colab.research.google.com/drive/1As0JIq6zxqsjeaVHmpxcRcccy7bqUIjy?usp=sharing

这与连接器线无关,但与我忽略的更基本的东西有关:投影。在我上面的例子中,整个地图都是扭曲的,但我只注意到我添加到地图中的连接线。所有的投影都是扭曲的,你需要根据你的目的选择正确的一个。我仍然需要学习更多关于投影的知识,但是现在我最终创建了一个自定义的UTM CRS,我的地图的中心作为UTM CRS的0,0坐标。

最新更新