Python xarray:具有低顶置轴坐标变换的极性pcolormesh

Python xarray:具有低顶置轴坐标变换的极性pcolormesh,python,matplotlib,python-xarray,polar-coordinates,Python,Matplotlib,Python Xarray,Polar Coordinates,我试图绘制一个二维的xarrayDataArray,表示一个以极坐标为参数的变量重要:θ坐标以度为单位,而不是弧度。以下代码段创建了一个示例数据集: 将numpy导入为np 将xarray作为xr导入 res_θ=20 θ=np.arange(0,360,res_θ) res_r=0.1 rs=np.arange(0,1,res\r) 数据=np.random.random((len(θ),len(rs))) my_da=xr.DataArray( 数据, 坐标=(θ,rs), dims=(“θ

我试图绘制一个二维的xarray
DataArray
,表示一个以极坐标为参数的变量重要:θ坐标以度为单位,而不是弧度。以下代码段创建了一个示例数据集:

将numpy导入为np
将xarray作为xr导入
res_θ=20
θ=np.arange(0,360,res_θ)
res_r=0.1
rs=np.arange(0,1,res\r)
数据=np.random.random((len(θ),len(rs)))
my_da=xr.DataArray(
数据,
坐标=(θ,rs),
dims=(“θ”,“r”),
)
我想将此数据绘制为极坐标
pcolormesh
。我还希望依靠xarray的绘图例程从尽可能多的功能(刻面、绘图定制等)中获益。Matplotlib的极轴投影假设
θ
角度以弧度表示:如果我选择简单的解决方案,我首先必须将
θ
坐标转换为弧度,但我不想修改阵列。我没有找到比复制数组并转换副本的
θ
更好的方法,例如:

def pcolormesh_polar_昂贵(da,*args,**kwargs):
da_tmp=da.copy()#我想避免这种情况
#获取x值
尝试:
x=args[0]
除索引器外:
x=da_tmp.dims[0]
da_tmp[x]=np.deg2rad(da_tmp[x])
尝试:
子地块=kwargs[“子地块”]
除KeyError外:
子地块_kws={}
返回da_tmp.plot.pcolormesh(
*args,
子地块=dict(投影=“极坐标”),
**夸尔斯
)
这将生成所需的绘图:

pcolormesh\u polar\u昂贵(my\u da,“theta”,“r”)

实际问题
然而,我希望避免重复数据:我的实际数据集要大得多。我做了一些研究,发现了Matplotlib的转换管道,我有一种感觉,我可以用它在绘图例程中动态插入此转换,但到目前为止,我无法让任何东西正常工作。有人知道我该怎么做吗?

多亏了@kmuehlbauer的建议和对问题的仔细研究,我成功地完成了我想要的

首先,我修改了测试数据,使其也包含单元元数据:

将numpy导入为np
将xarray作为xr导入
进口品脱
ureg=pint.UnitRegistry()
res_r=0.1
rs=np.arange(0,1,res\r)
res_θ=20
θ=np.arange(0,360,res_θ)
data=np.random.random((len(rs),len(θ)))
my_da=xr.DataArray(
数据,
坐标=(rs,θ),
dims=(“r”,“θ”),
)
my_da.theta.attrs[“单位”]=“度”
然后,我改进了kwargs处理以自动化单位转换,并创建了一个与
theta
维度关联的额外坐标:

def pcolormesh\u polar\u便宜(da,r=None,theta=None,add\u labels=False,**kwargs):
如果r为无:
r=da.dims[0]
如果θ为无:
θ=da.dims[1]
尝试:
θ单位=ureg.Unit(da[theta].attrs[“units”])
除KeyError外:
θ单位=ureg.rad
如果θ单位=ureg.rad:
θrad=f“{θ}rad”
θrad\u值=ureg.数量(da[θ].值,θ单位).至(ureg.rad).量级
da_plot=da.assign_坐标(**{theta_rad:(theta,theta_rad_值)})
da_图[theta_rad].attrs=da[theta].attrs
da_plot[theta_rad].attrs[“units”]=“rad”
其他:
θ_rad=θ
da_plot=da
kwargs[“x”]=θ
kwargs[“y”]=r
kwargs[“添加标签”]=添加标签
尝试:
子地块=kwargs[“子地块”]
除KeyError外:
子地块_kws={}
子地块_kws[“投影”]=“极坐标”
返回da_plot.plot.pcolormesh(
**夸尔斯,
子地块_kws=子地块_kws,
)
这里非常重要的一点是,
assign_coords()
返回从中调用的数据数组的副本,该副本的值实际上引用原始数组,因此除了创建额外的坐标之外,不会增加内存开销。按照@kmuehlbauer的建议修改数据数组很简单(只需将
da\u plot=da.assign\u coords(…)
替换为
da=da.assign\u coords(…)

然后我们得到相同的图(没有轴标签,因为我更改了默认值以隐藏它们):

pcolormesh\u polar\u便宜(my\u da,r=“r”,theta=“theta”)

您只需将另一个(例如θ2)坐标(包含弧度值)添加到数据数组中,并使用该坐标进行绘图。这样你就不必更改原始坐标。我考虑过了,但如果可能的话,我希望避免修改数据。数据不会被修改。将添加一个新坐标,而不更改原始数据和坐标。我对您的工作流程一无所知,但如果您为每个DataArray创建一次附加坐标(或者更好,在数据集级别),则只需计算一次。如果您尝试将其放入matplotlib转换管道,则必须为每个绘图计算它。干得好。您的方法现在可以处理这两种情况,包括附加坐标和不附加坐标。