Search code examples
pythonplotnetcdf

NetCDF: How can I script plotting at each time step?


I would like to create plot images from a NetCDF at each time step.

My NetCDF files look like this:

netcdf file:/C:/home/data/cmorph/test/reduced_cmorph_adjusted_spi_pearson_01.nc {
  dimensions:
    time = UNLIMITED;   // (240 currently)
    lat = 120;
    lon = 360;
  variables:
    float spi_pearson_01(time=240, lat=120, lon=360);
      :_FillValue = NaNf; // float
      :valid_min = -3.09; // double
      :valid_max = 3.09; // double
      :long_name = "Standard Precipitation Index (Pearson Type III distribution), 1-month scale";
      :_ChunkSizes = 1, 120, 360; // int

    int time(time=240);
      :units = "days since 1800-01-01 00:00:00";
      :_ChunkSizes = 1024; // int
      :_CoordinateAxisType = "Time";

    float lat(lat=120);
      :units = "degrees_north";
      :_CoordinateAxisType = "Lat";

    float lon(lon=360);
      :units = "degrees_east";
      :_CoordinateAxisType = "Lon";

  // global attributes:
  :title = "CMORPH Version 1.0BETA Version, daily precip from 00Z-24Z";
  :history = "Wed Feb 28 07:30:01 2018: C:\\home\\miniconda\\Library\\bin\\ncks.exe --dmn lon,0,,4 --dmn lat,0,,4 CMORPH_V1.0_ADJ_0.25deg-DLY_00Z_1998_2017.nc cmorph_reduced_adjusted.nc";
  :NCO = "4.7.1";
  :_CoordSysBuilder = "ucar.nc2.dataset.conv.DefaultConvention";
}

I like the plots produced by Panoply but I haven't worked out how to script it (I don't want to go through the GUI for this since I'll have roughly 1500 plots to create). I'm not wedded to Panoply per se, so if someone has a better idea please advise. I could hammer this out in matplotlib but it'd take me quite a while and wouldn't look as good as the Panoply plots. I'm trying to avoid doing much if any of the plotting myself, but maybe there's something out there that provides easy plotting of NetCDFs which can be called from a script (I typically use Python and Bash).


Solution

  • Example using xarray:

    import xarray as xr
    import matplotlib
    import matplotlib.pyplot as plt
    
    matplotlib.use('Agg')
    file_name = "reduced_cmorph_adjusted_spi_pearson_01.nc"
    with xr.open_dataset(file_name) as ds:
        for t in range(ds.time.shape[0]):
            da = ds.spi_pearson_01.isel(time=t)
            plt.figure()
            da.plot()
            plt.savefig('frame{}.png'.format(t))
    

    Non-scripting method if you don't mind using a few clicks in Panoply: create a lat/lon plot and then choose File->Export Animation . You can output individual time steps as JPG or PNG.