【问题标题】:Specify encoding/compression for many variables in xarray dataset when write to_netcdf写入 to_netcdf 时为 xarray 数据集中的许多变量指定编码/压缩
【发布时间】:2017-04-07 13:19:57
【问题描述】:

我一直在写出一些具有多个变量的 xarray.Datasets。目前,为了保持尺寸易于管理,我指定了编码,例如zlib,但需要逐个变量应用于变量(dataArray)。

将相同的编码参数应用于所有变量的好方法是什么?例如

<xarray.Dataset>
Dimensions:  (lat: 1440, lon: 2880)
Coordinates:
  * lat      (lat) float64 -90.0 -89.88 -89.75 -89.62 -89.5 -89.38 -89.25 ...
  * lon      (lon) float64 -180.0 -179.9 -179.8 -179.6 -179.5 -179.4 -179.2 ...
Data variables:
a1     (lat, lon) float64 nan nan nan nan nan nan nan nan 0.0 ...
b     (lat, lon) float64 nan nan nan nan nan nan 0.0 0.0 0.0 ...
c     (lat, lon) float64 nan nan nan nan nan nan nan nan 0.0 ...
d      (lat, lon) float64 nan nan nan nan nan nan nan nan 0.0 ...
e      (lat, lon) float64 nan nan nan nan nan nan nan nan 0.0 ...

当写出这个数据集时,我们会使用:

ds.to_netcdf(filename, encoding={'a1':{'zlib': True,'complevel': 5},'b':{'zlib': True,'complevel': 5},'c':{'zlib': True,'complevel': 5},'d':{'zlib': True,'complevel': 5},'e':{'zlib': True,'complevel': 5}})

对于更多变量,这会变得很冗长。一种选择是以顺序追加的方式将每个数据数组写入 netcdf,但是当数据集准备就绪时,这似乎也很复杂。

【问题讨论】:

    标签: python-xarray


    【解决方案1】:

    我只是动态创建编码参数:

    comp = dict(zlib=True, complevel=5)
    encoding = {var: comp for var in ds.data_vars}
    ds.to_netcdf(filename, encoding=encoding)
    

    【讨论】:

    • 谢谢 - 这是一个优雅的解决方案!
    • 我尝试了这个解决方案,它产生了一个 ValueError:scipy 后端的意外编码:['zlib','complevel']。通过安装 netcdf4 (pip install netcdf4) 并指定 engine='netcdf4' 解决。以防万一其他人有同样的问题。
    【解决方案2】:

    或者您可以将每个变量的编码信息存储在数据集中:

    comp = dict(zlib=True, complevel=5)
    for var in ds.data_vars: 
        var.encoding.update(comp)
    ds.to_netcdf(filename)
    

    【讨论】:

      【解决方案3】:

      https://github.com/pydata/xarray/discussions/5709

      这个答案导致_FillValue 丢失`:https://stackoverflow.com/a/40818232

      这个答案引发了“RuntimeError: NetCDF: Invalid argument”:https://stackoverflow.com/a/66333685

      但是,这行得通:

      encoding = {}
      encoding_keys = ("_FillValue", "dtype", "scale_factor", "add_offset", "grid_mapping")
      for data_var in ds.data_vars:
          encoding[data_var] = {key: value for key, value in ds[data_var].encoding.items() if key in encoding_keys}
          encoding[data_var].update(zlib=True, complevel=5)
      
      ds.to_netcdf(filename, encoding=encoding)
      

      【讨论】:

        猜你喜欢
        • 2020-07-29
        • 1970-01-01
        • 2020-12-06
        • 1970-01-01
        • 1970-01-01
        • 2012-02-17
        • 1970-01-01
        • 2022-01-03
        • 1970-01-01
        相关资源
        最近更新 更多