Python应用指南:获取行政区最小外接矩形

devtools/2024/10/21 1:06:25/

有的时候我们用行政区的面层进行裁剪的时候,特别是在基于行政区裁剪的渔网,因为行政边界本身就是不规则的原因,在边界的渔网匹配数据会出现匹配不上的问题,其实如果周边有数据完全可以采用最近匹配的原则,但是就是因为行政区裁太可丁可卯了,会丢失一部分数据,这个时候可以通过形成一个最小外接矩形的形式,可以让数据裁剪保持一个微妙的范围,不至于太大,又不至于没有二次处理的空间,第二个方面就是比如我们需要行政区里面的POI,以高德为例,因为行政区本身不是规则的,我们通过建立外接矩阵,这样获取其中的数据就不会出现丢失的情况了;

行政区边界获取部分,这里采用了阿里云旗下的数据可视化平台,其数据源本身也是来着高德地图,数据质量还是比较可靠的;

全国行政区划边界GeoJSON数据下载平台阿里云:DataV.GeoAtlas地理小工具系列 (aliyun.com)

这里把下载到本地的geojson或者json的文件路径改成自己的即可;

完整代码#运行环境Python 3.11

python">import geopandas as gp# 结果变量
resultMinLon = 99999.0  # 最小经度
resultMaxLon = -99999.0  # 最大经度
resultMinLat = 99999.0  # 最小纬度
resultMaxLat = -99999.0  # 最大纬度# 读取厦门市边界数据
# 注意:请确保文件路径正确
loadGeoData = gp.read_file("D:\\data\\厦门市.json")# 遍历每一行数据
for i in range(len(loadGeoData)):# 读取几何数据loadGeometry = loadGeoData.loc[i, "geometry"]# 检查几何数据类型,可能是单个多边形(Polygon)或多个多边形(MultiPolygon)if loadGeometry.geom_type == 'Polygon':# 单个多边形# 遍历多边形的所有顶点for z in range(len(loadGeometry.exterior.coords)):# 获取当前顶点的经度和纬度loadLon, loadLat = loadGeometry.exterior.coords[z]# 更新最小经度if loadLon < resultMinLon:resultMinLon = loadLon# 更新最大经度if loadLon > resultMaxLon:resultMaxLon = loadLon# 更新最小纬度if loadLat < resultMinLat:resultMinLat = loadLat# 更新最大纬度if loadLat > resultMaxLat:resultMaxLat = loadLatelif loadGeometry.geom_type == 'MultiPolygon':# 多个多边形# 遍历每个多边形for polygon in loadGeometry.geoms:# 遍历多边形的所有顶点for z in range(len(polygon.exterior.coords)):# 获取当前顶点的经度和纬度loadLon, loadLat = polygon.exterior.coords[z]# 更新最小经度if loadLon < resultMinLon:resultMinLon = loadLon# 更新最大经度if loadLon > resultMaxLon:resultMaxLon = loadLon# 更新最小纬度if loadLat < resultMinLat:resultMinLat = loadLat# 更新最大纬度if loadLat > resultMaxLat:resultMaxLat = loadLat# 结果输出
print("厦门市最小经度:", resultMinLon)
print("厦门市最大经度:", resultMaxLon)
print("厦门市最小纬度:", resultMinLat)
print("厦门市最大纬度:", resultMaxLat)

这里会直接打印出来两个对角线坐标,另外,因为数据源是高德的,用的是(GCJ-02)坐标系,最好先转成WGS84地理坐标系或者CGCS2000地理坐标系。如果需要可视化的话,可以跑一下下面的代码,与上面的区别就是通过调用了matplotlib包,使得结果可视化;

完整代码#运行环境Python 3.11

python">import geopandas as gp
import matplotlib.pyplot as plt
from matplotlib.patches import Rectangle# 配置 matplotlib 支持中文显示
plt.rcParams['font.family'] = ['SimHei']  # 使用黑体字体
plt.rcParams['axes.unicode_minus'] = False  # 正常显示负号# 结果变量
resultMinLon = 99999.0  # 最小经度
resultMaxLon = -99999.0  # 最大经度
resultMinLat = 99999.0  # 最小纬度
resultMaxLat = -99999.0  # 最大纬度# 读取厦门市边界数据
# 注意:请确保文件路径正确
loadGeoData = gp.read_file("D:\\data\\厦门市.json")# 遍历每一行数据
for i in range(len(loadGeoData)):# 读取几何数据loadGeometry = loadGeoData.loc[i, "geometry"]# 检查几何数据类型,可能是单个多边形(Polygon)或多个多边形(MultiPolygon)if loadGeometry.geom_type == 'Polygon':# 单个多边形# 遍历多边形的所有顶点for z in range(len(loadGeometry.exterior.coords)):# 获取当前顶点的经度和纬度loadLon, loadLat = loadGeometry.exterior.coords[z]# 更新最小经度if loadLon < resultMinLon:resultMinLon = loadLon# 更新最大经度if loadLon > resultMaxLon:resultMaxLon = loadLon# 更新最小纬度if loadLat < resultMinLat:resultMinLat = loadLat# 更新最大纬度if loadLat > resultMaxLat:resultMaxLat = loadLatelif loadGeometry.geom_type == 'MultiPolygon':# 多个多边形# 遍历每个多边形for polygon in loadGeometry.geoms:# 遍历多边形的所有顶点for z in range(len(polygon.exterior.coords)):# 获取当前顶点的经度和纬度loadLon, loadLat = polygon.exterior.coords[z]# 更新最小经度if loadLon < resultMinLon:resultMinLon = loadLon# 更新最大经度if loadLon > resultMaxLon:resultMaxLon = loadLon# 更新最小纬度if loadLat < resultMinLat:resultMinLat = loadLat# 更新最大纬度if loadLat > resultMaxLat:resultMaxLat = loadLat# 结果输出
print("厦门最小经度:", resultMinLon)
print("厦门最大经度:", resultMaxLon)
print("厦门最小纬度:", resultMinLat)
print("厦门最大纬度:", resultMaxLat)# 可视化
fig, ax = plt.subplots(figsize=(10, 10))# 绘制厦门市的边界
loadGeoData.plot(ax=ax, edgecolor='black', facecolor='lightblue')# 绘制最小外接矩形
min_rect = Rectangle((resultMinLon, resultMinLat), resultMaxLon - resultMinLon, resultMaxLat - resultMinLat,linewidth=2, edgecolor='red', facecolor='none', linestyle='--')
ax.add_patch(min_rect)# 标注最小和最大经度与纬度点
ax.scatter(resultMinLon, resultMinLat, color='red', label='最小边界')
ax.scatter(resultMaxLon, resultMaxLat, color='green', label='最大边界')
ax.annotate(f'({resultMinLon:.6f}, {resultMinLat:.6f})', (resultMinLon, resultMinLat), textcoords="offset points",xytext=(0, 10), ha='center')
ax.annotate(f'({resultMaxLon:.6f}, {resultMaxLat:.6f})', (resultMaxLon, resultMaxLat), textcoords="offset points",xytext=(0, 10), ha='center')# 添加图例
ax.legend()# 设置坐标轴范围
ax.set_xlim(resultMinLon - 0.01, resultMaxLon + 0.01)
ax.set_ylim(resultMinLat - 0.01, resultMaxLat + 0.01)# 显示图形
plt.title('厦门市边界及最小外接矩形')
plt.xlabel('经度')
plt.ylabel('纬度')
plt.grid(True)
plt.show()

下面这部分代码增加了一个功能:就是把这个矩形导出来,这里是把这个矩形导出来形成shp文件,修改文件路径的基础上再改一下保存位置路径即可;

完整代码#运行环境Python 3.11

python">import geopandas as gp
import matplotlib.pyplot as plt
from matplotlib.patches import Rectangle
from shapely.geometry import box# 配置 matplotlib 支持中文显示
plt.rcParams['font.family'] = ['SimHei']  # 使用黑体字体
plt.rcParams['axes.unicode_minus'] = False  # 正常显示负号# 结果变量
resultMinLon = 99999.0  # 最小经度
resultMaxLon = -99999.0  # 最大经度
resultMinLat = 99999.0  # 最小纬度
resultMaxLat = -99999.0  # 最大纬度# 读取厦门市边界数据
# 注意:请确保文件路径正确
loadGeoData = gp.read_file("D:\\data\\厦门市.json")# 遍历每一行数据
for i in range(len(loadGeoData)):# 读取几何数据loadGeometry = loadGeoData.loc[i, "geometry"]# 检查几何数据类型,可能是单个多边形(Polygon)或多个多边形(MultiPolygon)if loadGeometry.geom_type == 'Polygon':# 单个多边形# 遍历多边形的所有顶点for z in range(len(loadGeometry.exterior.coords)):# 获取当前顶点的经度和纬度loadLon, loadLat = loadGeometry.exterior.coords[z]# 更新最小经度if loadLon < resultMinLon:resultMinLon = loadLon# 更新最大经度if loadLon > resultMaxLon:resultMaxLon = loadLon# 更新最小纬度if loadLat < resultMinLat:resultMinLat = loadLat# 更新最大纬度if loadLat > resultMaxLat:resultMaxLat = loadLatelif loadGeometry.geom_type == 'MultiPolygon':# 多个多边形# 遍历每个多边形for polygon in loadGeometry.geoms:# 遍历多边形的所有顶点for z in range(len(polygon.exterior.coords)):# 获取当前顶点的经度和纬度loadLon, loadLat = polygon.exterior.coords[z]# 更新最小经度if loadLon < resultMinLon:resultMinLon = loadLon# 更新最大经度if loadLon > resultMaxLon:resultMaxLon = loadLon# 更新最小纬度if loadLat < resultMinLat:resultMinLat = loadLat# 更新最大纬度if loadLat > resultMaxLat:resultMaxLat = loadLat# 结果输出
print("厦门最小经度:", resultMinLon)
print("厦门最大经度:", resultMaxLon)
print("厦门最小纬度:", resultMinLat)
print("厦门最大纬度:", resultMaxLat)# 创建最小外接矩形的几何对象
bounding_box = box(resultMinLon, resultMinLat, resultMaxLon, resultMaxLat)# 创建 GeoDataFrame
bbox_gdf = gp.GeoDataFrame(geometry=[bounding_box], crs=loadGeoData.crs)# 保存为 Shapefile
output_path = "D:\\data\\厦门最小外接矩形.shp"
bbox_gdf.to_file(output_path)# 可视化
fig, ax = plt.subplots(figsize=(10, 10))# 绘制厦门市的边界
loadGeoData.plot(ax=ax, edgecolor='black', facecolor='lightblue')# 绘制最小外接矩形
min_rect = Rectangle((resultMinLon, resultMinLat), resultMaxLon - resultMinLon, resultMaxLat - resultMinLat,linewidth=2, edgecolor='red', facecolor='none', linestyle='--')
ax.add_patch(min_rect)# 标注最小和最大经度与纬度点
ax.scatter(resultMinLon, resultMinLat, color='red', label='最小边界')
ax.scatter(resultMaxLon, resultMaxLat, color='green', label='最大边界')
ax.annotate(f'({resultMinLon:.6f}, {resultMinLat:.6f})', (resultMinLon, resultMinLat), textcoords="offset points",xytext=(0, 10), ha='center')
ax.annotate(f'({resultMaxLon:.6f}, {resultMaxLat:.6f})', (resultMaxLon, resultMaxLat), textcoords="offset points",xytext=(0, 10), ha='center')# 添加图例
ax.legend()# 设置坐标轴范围
ax.set_xlim(resultMinLon - 0.01, resultMaxLon + 0.01)
ax.set_ylim(resultMinLat - 0.01, resultMaxLat + 0.01)# 显示图形
plt.title('厦门市边界及最小外接矩形')
plt.xlabel('经度')
plt.ylabel('纬度')
plt.grid(True)
plt.show()

忽然发现arcgis/arcgispro也可以生成这个最小外接矩形,直接检索【最小边界几何】,几何类型选择【按面积矩形】或者【按宽度矩形】都可,看需求,组选型选【ALL】这样会基于全部结果形成最外层的矩形;

结果如下;

文章仅用于分享个人学习成果与个人存档之用,分享知识,如有侵权,请联系作者进行删除。所有信息均基于作者的个人理解和经验,不代表任何官方立场或权威解读。


http://www.ppmy.cn/devtools/113398.html

相关文章

JZ2440开发板——S3C2440的时钟体系

参考博客 &#xff08;1&#xff09;S3C2440-裸机篇-05 | S3C2440时钟体系详解&#xff08;FCLK、PCLK、HCLK&#xff09; 一、三种时钟&#xff08;FCLK、HCLK、PCLK&#xff09; 如下图所示&#xff0c;S3C2440的时钟控制逻辑&#xff0c;给整个芯片提供三种时钟&#xff1…

Rust在Web开发中的优势是什么?

作为一种系统级编程语言&#xff0c;Rust在安全性和性能方面拥有得天独厚的优势&#xff0c;使其在Web开发领域展现出强大的竞争力。 1. 内存安全&#xff1a;告别内存泄漏和缓冲区溢出 Rust的核心优势之一就是其强大的内存安全机制。通过所有权系统和借用检查器&#xff0c;…

图论篇--代码随想录算法训练营第五十八天打卡|拓扑排序,dijkstra(朴素版),dijkstra(堆优化版)精讲

拓扑排序 题目链接&#xff1a;117. 软件构建 题目描述&#xff1a; 某个大型软件项目的构建系统拥有 N 个文件&#xff0c;文件编号从 0 到 N - 1&#xff0c;在这些文件中&#xff0c;某些文件依赖于其他文件的内容&#xff0c;这意味着如果文件 A 依赖于文件 B&#xff0…

PyQt5-loading-圆环加载效果

效果预览 代码实现 from PyQt5.QtCore import QSize, pyqtProperty, QTimer, Qt, QThread, pyqtSignal from PyQt5.QtGui import QColor, QPainter from PyQt5.QtWidgets import QApplication, QWidget, QHBoxLayout, QPushButton, QVBoxLayout, QLabel, QGridLayoutclass Cir…

WebSocket 协议

原文地址&#xff1a;xupengboo WebSocket WebSocket 是 HTML5 开始提供的一种在单个 TCP 连接上进行全双工通讯的协议。 在 WebSocket API 中&#xff0c;浏览器和服务器只需要完成一次握手&#xff0c;两者之间就直接可以创建持久性的连接&#xff0c;并进行双向数据传输。…

8.1 溪降技术:横渡绳

目录 8.1 横渡绳将其置于上下文中&#xff1a;观看视频课程电子书&#xff1a;横渡绳一级横渡绳&#xff1a;识别使用横渡绳固定到横渡绳V7提示&#xff1a;保持张力中间点通过横渡绳上的中间点固定到锚点总结 8.1 横渡绳 绳上移动 横渡绳是一条水平安全绳&#xff0c;探险者可…

2024自学手册——网络安全(黑客技术)

&#x1f91f; 基于入门网络安全/黑客打造的&#xff1a;&#x1f449;黑客&网络安全入门&进阶学习资源包 前言 什么是网络安全 网络安全可以基于攻击和防御视角来分类&#xff0c;我们经常听到的 “红队”、“渗透测试” 等就是研究攻击技术&#xff0c;而“蓝队”、…

51单片机-AT24C02-实验2-秒表实验(可参考上一节)

利用定时器去对按键和数码管进行扫描(Whappy) main.c #include <REGX52.H> #include "LCD1602.h" #include "AT24C02.h" #include "Delay.h" #include "Timer0.h" #include "Nixie.h" #include "Key.h"un…