GeoPandas:计算点列表与国家的距离并转为公里及相关确认
解决多边形与点的距离单位转换及距离计算逻辑问题
先回应你的第二个疑问:你推测的完全没错!z=i.distance(world.geometry[3])计算的就是点到多边形的最短距离,并非到多边形质心的距离。Geopandas的distance方法针对点与多边形的组合,会自动计算点到多边形边界上最近点的距离(基于当前坐标系),完全符合你的需求。
接下来解决距离单位从度数转公里的核心问题:
你的原始数据采用的是WGS84经纬度坐标系(EPSG:4326),这种坐标系下的distance方法返回的是度数差,无法直接代表地面实际距离(不同纬度的1度地面长度差异很大)。这里有两种实用的解决思路:
方法1:投影到米/公里单位的坐标系后计算距离
我们可以将数据转换到适合的投影坐标系,比如加拿大专用的EPSG:3978(Canada Atlas Lambert)——这个投影针对加拿大区域做了优化,距离计算精准,单位为米。转换完成后计算距离,再除以1000即可得到公里数:
import geopandas as gpd # 读取原始数据集 world = gpd.read_file(gpd.datasets.get_path('naturalearth_lowres')) cities = gpd.read_file(gpd.datasets.get_path('naturalearth_cities')) # 转换到加拿大专用投影(单位:米) canada_proj = world[world.name == 'Canada'].to_crs(epsg=3978) cities_proj = cities.to_crs(epsg=3978) # 计算每个城市到加拿大的最短距离,转换为公里 distances_km = [] for city_geom in cities_proj.geometry: dist_m = city_geom.distance(canada_proj.geometry.iloc[0]) distances_km.append(dist_m / 1000) print(distances_km)
如果需要全球通用的投影方案,可以改用EPSG:4087(World Equidistant Cylindrical),它的经线距离比例一致,单位同样是米,适合跨大范围的距离计算。
方法2:直接用测地线计算球面距离(无需投影)
如果不想转换坐标系,可借助pyproj的Geod类直接计算经纬度对应的球面最短路径距离(单位为米),这种方法更适配全球范围的计算场景:
import geopandas as gpd from pyproj import Geod # 初始化WGS84测地线计算器 geod = Geod(ellps='WGS84') world = gpd.read_file(gpd.datasets.get_path('naturalearth_lowres')) cities = gpd.read_file(gpd.datasets.get_path('naturalearth_cities')) # 获取加拿大的多边形几何对象 canada_geom = world.geometry[3] distances_km = [] for city_geom in cities.geometry: # 计算点到多边形的测地线最短距离(米) dist_m = geod.geometry_distance(city_geom, canada_geom) distances_km.append(dist_m / 1000) print(distances_km)
小提示
- 方法1适合区域范围的计算(比如仅关注加拿大周边),投影后的平面距离误差极小;
- 方法2适合全球范围的计算,直接贴合地球球面的实际最短路径,结果更精准。
内容的提问来源于stack exchange,提问作者The Oracle




