Python中地理空间数据的分箱与可视化实现求助
1x1度网格分箱并按密度可视化的实现方案
嘿,刚入坑Python地理空间数据的话,这个需求完全可以用numpy+matplotlib+cartopy搞定,我给你一步步来:
第一步:先处理经纬度格式
你给的经度是280这种0-360范围的(西经),但大多数地图库默认用-180到180的经度范围,所以先转一下:
import numpy as np # 假设你的数组已经是numpy数组,如果不是先转成numpy格式 variable_lats = np.array([20.099339, 20.142488, 20.101004, ..., -38.988274, -38.988274, -38.9924]) variable_lons = np.array([280.017, 279.97015, 280.03192, ..., 22.829168, 22.829168, 22.834965]) # 转换经度到-180~180的标准范围 variable_lons = np.where(variable_lons > 180, variable_lons - 360, variable_lons)
第二步:1x1度网格分箱计算密度
用numpy的histogram2d函数直接统计每个网格里的点数(也就是你要的密度):
# 定义1度间隔的网格边界 lon_bins = np.arange(-180, 181, 1) # 从-180到180,每步1度 lat_bins = np.arange(-90, 91, 1) # 从-90到90,每步1度 # 计算每个网格的点数(密度) density, lon_edges, lat_edges = np.histogram2d( variable_lons, variable_lats, bins=[lon_bins, lat_bins] ) # 注意:histogram2d返回的density是(lon箱数-1, lat箱数-1)的数组,刚好对应每个1x1度网格
第三步:可视化密度分布图
用cartopy来画带地图底图的可视化,这样比纯热力图更直观:
import matplotlib.pyplot as plt import cartopy.crs as ccrs from cartopy.feature import NaturalEarthFeature # 设置地图投影 fig, ax = plt.subplots( figsize=(12, 6), subplot_kw={'projection': ccrs.PlateCarree()} ) # 画密度热力图,这里要转置density,因为pcolormesh是(y,x)的顺序 im = ax.pcolormesh( lon_edges, lat_edges, density.T, cmap='YlOrRd', # 选个适合密度展示的配色,你也可以换'viridis'或'Blues' transform=ccrs.PlateCarree() ) # 添加地图元素:海岸线、陆地轮廓 coastline = NaturalEarthFeature('physical', 'coastline', '110m', edgecolor='black', facecolor='none') ax.add_feature(coastline) # 可选:根据你的数据范围调整显示区域,避免空范围 ax.set_extent([variable_lons.min()-2, variable_lons.max()+2, variable_lats.min()-2, variable_lats.max()+2]) # 添加颜色条和标题 plt.colorbar(im, ax=ax, label='网格内数据点密度') plt.title('1x1度网格数据点密度分布') plt.show()
额外小贴士
- 如果你的数据里有缺失值(NaN),先过滤掉再处理:
# 过滤所有含NaN的行 mask = ~np.isnan(variable_lats) & ~np.isnan(variable_lons) filtered_lats = variable_lats[mask] filtered_lons = variable_lons[mask] # 之后用过滤后的数组去做分箱和可视化 - 要是不想装cartopy,也可以直接用matplotlib的
pcolormesh画纯热力图,只是少了地图底图的参考性。
内容的提问来源于stack exchange,提问作者Balazagi




