
本文介绍如何正确合并由多个 NetCDF 文件读取得到的 xarray.Dataset 列表,重点纠正常见的 extend 误用问题,并使用 xr.concat() 高效构建统一时空维度的数据集。
本文介绍如何正确合并由多个 netcdf 文件读取得到的 xarray.dataset 列表,重点纠正常见的 `extend` 误用问题,并使用 `xr.concat()` 高效构建统一时空维度的数据集。
在处理多文件气象或气候数据(如 CMIP6 的 CanESM5 输出)时,常需批量读取、裁剪并合并多个 xarray.Dataset。初学者易混淆 list.extend() 与 list.append() ——前者将可迭代对象(如 Dataset 的变量/坐标序列)逐项展开插入列表,导致 fwi_list 变成一堆零散 DataArray 或坐标而非 Dataset;后者才真正将每个完整 Dataset 作为独立元素存入列表,为后续拼接奠定基础。
正确做法是:先用 append() 构建 Dataset 列表,再统一调用 xr.concat() 沿指定维度(如 'time')合并。注意必须确保所有 Dataset 在拼接维度上互斥且有序(例如各文件时间范围不重叠),否则需预先排序或去重。以下为优化后的完整流程:
import glob
import xarray as xr
all_fwi = glob.glob("D:/FWI_future/fwi_intermediary/fwi_day_CanESM5_ssp245*.nc")
fwi_list = []
for i in all_fwi:
# 读取并精简变量
infile = xr.open_dataset(
i,
drop_variables=[
'TEMP_wDC_2014', 'ffmcPREV_2014', 'dcPREV_2014', 'dmcPREV_2014',
'SeasonActive_2014', 'DCf_2014', 'rw_2014', 'CounterSeasonActive_2014',
'ffmc', 'dc', 'dmc', 'isi', 'bui', 'TEMP', 'RH', 'RAIN', 'WIND'
]
)
# 空间裁剪(注意:lon 范围含 360° 偏移,需确认是否需 mod 360)
yt = infile.sel(lon=slice(218.9931, 236.2107), lat=slice(60, 69.64794))
# 时间裁剪与季节筛选
yt1 = yt.sel(time=slice('2020-01-01', '2060-12-31'))
yt2 = yt1.sel(time=yt1.time.dt.month.isin([3, 4, 5, 6, 7, 8, 9]))
fwi_list.append(yt2) # ✅ 关键:使用 append 而非 extend
# 统一拼接(推荐 dim='time',自动对齐坐标)
final_dat = xr.concat(fwi_list, dim='time')
# 可选:按时间排序(若文件顺序混乱)
final_dat = final_dat.sortby('time')
# 保存为 NetCDF(自动使用 NETCDF4 格式)
final_dat.to_netcdf("fwi_merged_2020-2060_summer.nc")
⚠️ 注意事项:
- xr.concat() 默认要求拼接维度(如 'time')在各 Dataset 中无重叠且单调;若存在重叠,添加参数 combine_attrs='override' 或 data_vars='minimal' 控制变量合并策略;
- 若各文件时间坐标类型不一致(如 object vs datetime64),需先统一:ds['time'] = ds['time'].astype('datetime64[ns]');
- 大数据量时,建议启用 dask 延迟加载:xr.open_dataset(..., chunks={'time': 100}),再拼接以节省内存;
- 不要将 xr.concat() 放入循环内——每次调用均触发全量复制,性能急剧下降。
最终生成的 final_dat 是一个标准 xarray.Dataset,具备完整坐标、属性和数据变量,可直接用于分析、可视化或导出为 NetCDF 文件,完全满足后续科研或业务处理需求。











