marEx.detect.smoothed_rolling_climatology

marEx.detect.smoothed_rolling_climatology(da, window_year_baseline=15, smooth_days_baseline=21, dimensions=None, coordinates=None, use_temp_checkpoints=False)[source]

Compute a smoothed rolling climatology using the previous window_year_baseline years of data and reassemble it to match the original data structure. Years without enough previous data will be filled with NaN.

Parameters:
  • da (xarray.DataArray) – Input data with time coordinate

  • window_year_baseline (int, default=15) – Number of years to include in each climatology window

  • smooth_days_baseline (int, default=21) – Number of days for temporal smoothing window

  • dimensions (dict, optional) – Mapping of dimensions to names in the data

  • coordinates (dict, optional) – Mapping of coordinates to names in the data

  • use_temp_checkpoints (bool)

Returns:

Smoothed rolling climatology with same shape as input data

Return type:

xarray.DataArray

Examples

Basic smoothed rolling climatology:

>>> import xarray as xr
>>> import marEx
>>>
>>> # Load SST data
>>> sst = xr.open_dataset('sst_data.nc', chunks={}).sst.chunk({'time': 30})
>>>
>>> # Compute smoothed rolling climatology
>>> smooth_clim = marEx.smoothed_rolling_climatology(
...     sst,
...     window_year_baseline=15,
...     smooth_days_baseline=21
... )
>>> print(smooth_clim.shape)
(7305, 180, 360)

Comparing different smoothing windows:

>>> # Short smoothing - more day-to-day variability
>>> clim_short = marEx.smoothed_rolling_climatology(
...     sst, smooth_days_baseline=7
... )
>>>
>>> # Long smoothing - smoother seasonal cycle
>>> clim_long = marEx.smoothed_rolling_climatology(
...     sst, smooth_days_baseline=61
... )
>>>
>>> # Compare variability
>>> var_short = clim_short.std(dim='time').mean().compute()
>>> var_long = clim_long.std(dim='time').mean().compute()
>>> print(f"Variability: short={var_short:.3f}, long={var_long:.3f}")

Climatology for anomaly computation:

>>> # Compute smoothed climatology then anomalies
>>> climatology = marEx.smoothed_rolling_climatology(sst)
>>> anomalies = sst - climatology
>>>
>>> # Check that anomalies have reasonable properties
>>> print(f"Anomaly mean: {anomalies.mean().compute():.6f}")
>>> print(f"Anomaly std: {anomalies.std().compute():.3f}")

Unstructured data processing:

>>> # ICON ocean data
>>> icon_sst = xr.open_dataset('icon_sst.nc', chunks={}).to.chunk({'time': 25})
>>> icon_smooth_clim = marEx.smoothed_rolling_climatology(
...     icon_sst,
...     dimensions={"time": "time", "x": "ncells"},
...     coordinates={"time": "time", "x": "lon", "y": "lat"},
...     window_year_baseline=10,
...     smooth_days_baseline=31
... )

Effect of smoothing on seasonal cycle:

>>> # Raw rolling climatology (no temporal smoothing)
>>> raw_clim = marEx.rolling_climatology(sst, window_year_baseline=15)
>>>
>>> # Smoothed rolling climatology
>>> smooth_clim = marEx.smoothed_rolling_climatology(
...     sst, window_year_baseline=15, smooth_days_baseline=21
... )
>>>
>>> # Compare seasonal cycle smoothness
>>> # Extract annual cycle for a point
>>> point_raw = raw_clim.isel(lat=90, lon=180).sel(time='2010')
>>> point_smooth = smooth_clim.isel(lat=90, lon=180).sel(time='2010')
>>>
>>> print(f"Raw climatology range: {(point_raw.max() - point_raw.min()).compute():.3f}")
>>> print(f"Smooth climatology range: {(point_smooth.max() - point_smooth.min()).compute():.3f}")

Performance considerations:

>>> # Efficient implementation smooths raw data first, then computes climatology
>>> # This is more memory-efficient than smoothing the climatology
>>> large_sst = sst.chunk({'time': 25, 'lat': 45, 'lon': 90})
>>> efficient_clim = marEx.smoothed_rolling_climatology(large_sst)