You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何从Shapely MultiPolygon对象中检测内多边形并避免填充?

检测并处理Shapely MultiPolygon中的内多边形(洞)

核心原理

Shapely的Polygon对象天然区分外边界(exterior)和内边界(interiors,即洞)——五大湖、黑海、里海这类区域本质是陆地多边形的“洞”。只要正确识别并传递这些边界给绘图库,就能实现洞区域不填充的效果。

解决步骤

  • 遍历MultiPolygon中的每个子Polygon对象:通过MultiPolygon.geoms属性获取所有子Polygon。
  • 利用绘图库的自动填充规则:matplotlib/cartopy支持根据多边形环的缠绕方向自动识别洞,无需手动判断,只需将Polygon的完整边界(外+内)传入绘图函数。
  • Shapefile适配:用geopandas读取Shapefile时,会自动将带洞的多边形解析为包含interiors的Shapely Polygon对象,后续处理逻辑完全一致。

修改后的测试脚本

import matplotlib.pyplot as plt
import cartopy.crs as ccrs
from shapely import geometry
import random
import pickle

! wget -nc https://thredds-su.ipsl.fr/thredds/fileServer/ipsl_thredds/brocksce/tmp/polys.pickle

with open('./polys.pickle', "rb") as poly_file:
    polygons = pickle.load(poly_file)

fig = plt.figure(figsize=(10,5))
ax = fig.add_subplot(1, 1, 1, projection=ccrs.Robinson(10))

transform = ccrs.Geodetic()

for polygon in polygons.geoms:
    random_color = "#"+''.join([random.choice('0123456789ABCDEF') for i in range(6)])
    # 推荐方式:用cartopy原生方法自动处理洞
    ax.add_geometries([polygon], crs=transform, facecolor=random_color, edgecolor="black", lw=0.5)
    
    # 手动处理方式(适合细粒度控制)
    # coords = list(polygon.exterior.coords)
    # for interior in polygon.interiors:
    #     coords.extend(list(interior.coords))
    # ax.fill(*zip(*coords), transform=transform, color=random_color, lw=0.5, edgecolor="black")

ax.set_global()
ax.gridlines()
plt.show()

关键说明

  • ax.add_geometries是最优方案:cartopy原生支持Shapely几何对象,会自动识别Polygon的interiors作为洞,填充时自动挖空这些区域。
  • 手动处理逻辑:若需更精细控制,可依次传入外边界和所有内边界的坐标,matplotlib默认的非零环绕数规则会自动区分填充区域和洞。
  • Shapefile读取:使用geopandas.read_file()读取Shapefile后,GeoDataFrame的geometry列会自动生成带正确内外边界的Shapely对象,直接套用上述绘制逻辑即可。

内容的提问来源于stack exchange,提问作者PBrockmann

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.09 03:35:20