如何简化Shapely中的边界几何

问题描述 投票:0回答:2

我正在使用 shapely 来做 GIS,但是在将每个邮政编码的几何图形加载到内存中时遇到内存错误,因为几何图形是如此锯齿状且复杂。

我想通过尽可能减少边界点的数量来使形状在内存中更小,同时又不会过度扭曲形状。使用凸包似乎是一种潜在的答案,因为可以简单地从边界上丢弃很多点。我想知道是否已经有一些东西可以解决这个问题。

python gis shapely
2个回答
12
投票

尝试使用几何体的简化方法,指定公差距离。


0
投票

我遇到了这篇旧帖子,因为我遇到了类似的问题。我的解决方案如下:

从区域蒙版生成多边形。

这里有两个区域。

import matplotlib.pyplot as plt
import shapely.geometry
import cv2
import numpy as np

# gen. mask
mask=np.zeros((600,600),dtype=bool)
mask[300:500,300:500]=True
mask[:150,30:120]=True
mask[70:120,30:220]=True
mask[100:200,200:260]=True

# get contours == polygon
contours, _ = cv2.findContours(mask.astype(np.uint8),  # cv2 requires special types
                               cv2.RETR_TREE,
                               cv2.CHAIN_APPROX_NONE)
contours = [i.reshape((-1, 2)) for i in contours]

简化多边形

def simplify(polygon, tolerance = .1):
    """ Simplify a polygon with shapely.
    Polygon: ndarray
        ndarray of the polygon positions of N points with the shape (N,2)
    tolerance: float
        the tolerance
    """
    poly = shapely.geometry.Polygon(i.reshape((-1, 2)))
    poly_s = poly.simplify(tolerance=tolerance)
    # convert it back to numpy
    return np.array(poly_s.boundary.coords[:])

# Simplify all contours
contours_s = []
for i in contours:
    contours_s.append(simplify(i.reshape((-1, 2))))

剧情

plt.figure(figsize=(4,4))
plt.imshow(mask, label='2D mask')

for i, c_i in enumerate(contours_s):
    plt.plot(*c_i.reshape((-1, 2)).T, '-', label=f'cv2 contours {i}')
    
for i, c_i in enumerate(contours_s):
    plt.plot(*c_i.T, 'o', label=f'shapely simplify {i}')
    
plt.legend()
plt.tight_layout()

© www.soinside.com 2019 - 2024. All rights reserved.