我正在为不同的时间范围创建多个等值线图(因为我想做一个 gif),想知道是否有任何方法可以固定每个地图的比例以便于进行视觉比较?
我现在的代码如下
years = range(2000, 2020)
# Create the images for each year
images = []
for year in years:
fig, ax = plt.subplots(figsize=(10, 10))
agg.plot(column="nac_"+str(year), cmap='Blues', ax=ax, legend=True, legend_kwds={'label': f'Births in {year}'})
ax.set_title(f'Number of births in {year}')
ax.set_axis_off()
plt.axis('equal')
plt.tight_layout()
plt.savefig(f'births_{year}.png', dpi=150)
plt.close()
images.append(imageio.imread(f'births_{year}.png'))
# Save the images as a gif
imageio.mimsave('births.gif', images, fps=4)
输出看起来像这样
从上面看,很明显,由于色标的界限发生了变化,我无法真正观察到各地区的出生人数是如何下降的。
这里是一个演示代码,演示了专题地图的标准化颜色条的使用。阅读代码中的注释以获得更多解释。
import numpy as np
import matplotlib.pyplot as plt
import matplotlib as mpl
from matplotlib import colorbar, colors
import cartopy.crs as ccrs
import cartopy.feature as cf
X = [9.95, 11.06, 12.18, 9.13, 8.40,
11.08, 11.05, 9.86, 12.50, 7.83,
10.93, 11.81, 10.02, 8.54, 10.29]
Y = [49.74, 47.43, 49.62, 47.62, 48.48,
47.09, 49.53, 48.56, 48.29, 48.02,
49.15, 48.34, 50.22, 49.53, 47.34]
# Base values of thematic data
Z = np.array([2.33, -0.52, 0.97,
-0.50, 0.21, 0.40,
-1.69, 1.37, -1.79,
-0.09, 0.96, 0.12,
-0.03, 1.36, -0.37])
# Data statistics
zmin, zmax = min(Z), max(Z)
zavg = 0.5 + (zmin+zmax)/2
# Make-up more data sets for demo purposes
Z1 = [Z, 8+Z, Z-4]
Z2 = [9*Z, zavg+4*Z, -5*Z-zavg]
# Here I get 6 data sets for 2x3 subplots
ZZ = [Z1, Z2]
# Compute values for `norm`
# vmin: minimum of all possible values from all data sets
# vmax: maximum of all possible values ...
vmin = min(np.array(ZZ).flat)
vmax = max(np.array(ZZ).flat)
# Finally, compute norm
mynorm = mpl.colors.Normalize(vmin=vmin, vmax=vmax)
# Choose a colormap
mycmap = "plasma" #viridis
# visualization
numCol, numRow = 3, 2
fig,ax = plt.subplots(ncols=numCol, nrows=numRow, figsize=(13,5),
subplot_kw={'projection': ccrs.PlateCarree()})
fig.tight_layout()
# This plots 2x3 array of maps
# Each map has the same colorbar for its thematic representation
for col in range(numCol):
for row in range(numRow):
ax[row,col].set_extent([7.2, 13.7, 46.8, 50.7])
ax[row,col].add_feature(cf.BORDERS, linewidth=0.3)
ax[row,col].set_aspect('equal')
ax[row,col].set_title("Row/Col: "+str(row)+"|"+str(col))
mmin, mmax = min(ZZ[row][col]), max(ZZ[row][col])
print(f"Row:{row}, col:{col}, minVal:{mmin:.2f}, maxVal:{mmax:.2f}")
ax[row,col].scatter(X, Y, c=ZZ[row][col], s=100,
cmap = mycmap,
norm = mynorm,
edgecolors='none',
transform=ccrs.PlateCarree())
fig.colorbar(mpl.cm.ScalarMappable(norm=mynorm, cmap=mycmap),
ax=ax[row,col],
aspect = 12,
shrink=0.79)
输出地图数组:
请注意,6 个数据集中的每个数据集都有不同的最小/最大值。如果不使用
normalized
颜色图,它们的颜色条将不同。
上面的代码应该为您提供适应您的用例的想法。
因为所有的颜色条都是一样的,在实践中你只需要绘制其中的一个。