在 3D xarray 中按月份访问数据
Access data by month number in 3D xarray
我有给定年份的一月、二月、三月、四月、十月、十一月和十二月的数据数组 (361x361)。
到目前为止,我一直将它们存储在一年中每个月的单独 netcdfs 中(例如 03.nc、10.nc)
我想将所有月份合并为一个 netcdf,这样我就可以做类似的事情:
march_data = data.sel(month='03')
或者 data.sel(month=3))
到目前为止,我只能将月度数据堆叠在一个 361x361x7 数组中,而且它的索引毫无帮助,因此要获取三月份的数据,您需要执行 data[:,:,2] 并获取十月份的数据[:,:,4]。显然 2 和 4 并不直观地对应于三月和十月。这部分是因为 python 是从零开始索引的,部分是因为我错过了夏季月份。我可以将 nan 字段放入缺失的月份,但这不能解决 index-0 问题。
我目前的尝试:
data = xarray.Dataset( data_vars={'ice_type':(['x','y','time'],year_array),},
coords={'lon':(['x','y'],lon_target),
'lat':(['x','y'],lat_target),
'month_number':(['time'],month_int)})
这里year_array
是一个361x361x7的numpy数组,month_int
是一个列表,将year_array
的第三个索引映射到月份数:[1,2,3,4,10,11,12]
.
当我尝试使用 oct = data.sel(month_number=10)
获取 Oct 数据时,它会抛出一个错误。
附带说明一下,我知道可能会找到一个解决方案 here,但老实说我不明白它是如何工作的。我的困惑主要是基于他们如何同时使用 'time' 作为字典键和时间列表。
我想我已经写了一个辅助函数来做类似的事情:
def combine_new_ds_dim(ds_dict, new_dim_name):
"""
Combines a dictionary of datasets along a new dimension using dictionary keys
as the new coordinates.
Parameters
----------
ds_dict : dict
Dictionary of xarray Datasets or dataArrays
new_dim_name : str
The name of the newly created dimension
Returns
-------
xarray.Dataset
Merged Dataset or DataArray
Raises
------
ValueError
If the values of the input dictionary were of an unrecognized type
"""
expanded_dss = []
for k, v in ds_dict.items():
expanded_dss.append(v.expand_dims(new_dim_name))
expanded_dss[-1][new_dim_name] = [k]
new_ds = xr.concat(expanded_dss, new_dim_name)
return new_ds
如果您拥有个人 netcdf 中的所有数据,那么您应该能够将它们导入个人 dataArray
中。假设你已经这样做了,那么你可以做
month_das = {
1: january_da,
2: february_da,
...
12: december_da
}
year_data = combine_new_ds_dim(month_das, 'month')
这将是沿新维度 month
的所有数据与所需坐标的串联。我认为函数的主循环很容易分开,如果你想单独使用的话。
编辑:
对于将来查看此内容的任何人来说,使用内置 xarray 函数可以更轻松地完成此操作。你可以沿着一个新的维度连接
year_data = xr.concat([january_da, february_da, ..., december_da], dim="month")
这将创建一个新的 dataArray
,其组成数组沿新维度连接,但没有该维度上的坐标。要添加坐标,
year_data["month"] = [1, 2, ..., 12]
此时 year_data
将沿着新维度“月”连接起来,并且沿着该维度将具有所需的坐标。
我有给定年份的一月、二月、三月、四月、十月、十一月和十二月的数据数组 (361x361)。
到目前为止,我一直将它们存储在一年中每个月的单独 netcdfs 中(例如 03.nc、10.nc)
我想将所有月份合并为一个 netcdf,这样我就可以做类似的事情:
march_data = data.sel(month='03')
或者 data.sel(month=3))
到目前为止,我只能将月度数据堆叠在一个 361x361x7 数组中,而且它的索引毫无帮助,因此要获取三月份的数据,您需要执行 data[:,:,2] 并获取十月份的数据[:,:,4]。显然 2 和 4 并不直观地对应于三月和十月。这部分是因为 python 是从零开始索引的,部分是因为我错过了夏季月份。我可以将 nan 字段放入缺失的月份,但这不能解决 index-0 问题。
我目前的尝试:
data = xarray.Dataset( data_vars={'ice_type':(['x','y','time'],year_array),},
coords={'lon':(['x','y'],lon_target),
'lat':(['x','y'],lat_target),
'month_number':(['time'],month_int)})
这里year_array
是一个361x361x7的numpy数组,month_int
是一个列表,将year_array
的第三个索引映射到月份数:[1,2,3,4,10,11,12]
.
当我尝试使用 oct = data.sel(month_number=10)
获取 Oct 数据时,它会抛出一个错误。
附带说明一下,我知道可能会找到一个解决方案 here,但老实说我不明白它是如何工作的。我的困惑主要是基于他们如何同时使用 'time' 作为字典键和时间列表。
我想我已经写了一个辅助函数来做类似的事情:
def combine_new_ds_dim(ds_dict, new_dim_name):
"""
Combines a dictionary of datasets along a new dimension using dictionary keys
as the new coordinates.
Parameters
----------
ds_dict : dict
Dictionary of xarray Datasets or dataArrays
new_dim_name : str
The name of the newly created dimension
Returns
-------
xarray.Dataset
Merged Dataset or DataArray
Raises
------
ValueError
If the values of the input dictionary were of an unrecognized type
"""
expanded_dss = []
for k, v in ds_dict.items():
expanded_dss.append(v.expand_dims(new_dim_name))
expanded_dss[-1][new_dim_name] = [k]
new_ds = xr.concat(expanded_dss, new_dim_name)
return new_ds
如果您拥有个人 netcdf 中的所有数据,那么您应该能够将它们导入个人 dataArray
中。假设你已经这样做了,那么你可以做
month_das = {
1: january_da,
2: february_da,
...
12: december_da
}
year_data = combine_new_ds_dim(month_das, 'month')
这将是沿新维度 month
的所有数据与所需坐标的串联。我认为函数的主循环很容易分开,如果你想单独使用的话。
编辑:
对于将来查看此内容的任何人来说,使用内置 xarray 函数可以更轻松地完成此操作。你可以沿着一个新的维度连接
year_data = xr.concat([january_da, february_da, ..., december_da], dim="month")
这将创建一个新的 dataArray
,其组成数组沿新维度连接,但没有该维度上的坐标。要添加坐标,
year_data["month"] = [1, 2, ..., 12]
此时 year_data
将沿着新维度“月”连接起来,并且沿着该维度将具有所需的坐标。