Xarray读取文件中的数据作为坐标,显然是索引坐标,如何将实际数据从坐标转换为数据变量?

时间:2020-05-22 18:11:07

标签: python-xarray

我正在使用以下文件:

https://satdat.ngdc.noaa.gov/sem/poes/data/processed/ngdc/uncorrected/full/2013/metop01/poes_m01_20130525_proc.nc

当我使用xarray读取它时,

ds = xr.open_dataset('poes_m01_20130525_proc.nc')

所有变量都作为坐标读取,其中至少有一些作为索引坐标。我只知道最后一点,因为当我尝试使用将它们转换为变量时,

ds.reset_coords()

我得到了错误

ValueError: cannot remove index coordinates with reset_coords.  The error appears to include all of the variables (there is a very long list).  

我可以将所有坐标变量转换为numpy数组,并手动重建新的数据集。但是,我对xarray非常陌生。有没有更优雅的方法可以做到这一点?例如,我可以将分度坐标转换为非分度坐标然后使用reset_coords吗?另外,如何分辨哪些坐标是索引坐标,哪些不是索引坐标?

或者更好的是,在读取我不知道要使用的文件时,应该使用一些选项吗?我在文档中没有发现任何建议可以做到这一点,但是文档中有很多我不理解的地方。

感谢您的帮助!

1 个答案:

答案 0 :(得分:1)

您已经猜到,要能够将坐标转换为数据变量,它必须是非索引坐标。您会认识到索引坐标,因为列出坐标时,它们前面有一个*。在您的示例中,似乎每个变量都假定是它自己的坐标(不知道为什么,我不是NetCDF专家)。

要将索引坐标转换为非索引坐标,可以使用reset_index,它要求指定要重置的索引。我冒昧地假设数据集中的前几个坐标已正确设置为坐标,其余应为数据变量。在这种情况下,以下代码可以解决问题:

var_names = list(
    set(ds.dims) - 
    {"time", "year", "day", "msec", "satID", "sat_direction", "alt", "lat", "lon"}
)
clean_ds = ds.reset_index(var_names).reset_coords()

这给我们留下了一个不太有用的数据集。 reset_index在每个变量名称的末尾添加了一个_(以将非索引坐标与具有相同名称的维区分开)。您可能想要做与其他答案类似的事情:Xarray: Make two DataArrays in the same Dataset use the same coordinate system

一些想法:

获取所有变量,将time作为维度

coord_names = ["time", "year", "day", "msec", "satID", "sat_direction", "alt", "lat", "lon"]
clean_ds = clean_ds.reset_index(coord_names + [])
clean_ds = clean_ds.rename({name: "time_" for name in clean_ds.dims})

然后,重命名变量和坐标(和time_暗号)以删除名称中的尾随下划线:

clean_ds.rename({f"{name}_": name for name in var_names+coord_names})

如果我们使用rename_vars的维度time_不会被重命名,则可以在以后重命名以保持时间协调和暗淡的不同。

所有重命名和重组之后,原始数据集的属性可以再次添加到clean_ds

for var_name in ds.coords:
    clean_ds[var_name] = clean_ds[var_name].assign_attrs(ds[var_name].attrs)