Coastal Masks Using ConvolutionsΒΆ

import xarray as xr
import numpy

import hvplot.xarray
import holoviews as hv

from scipy.signal import convolve2d
data_file = '/mnt/GEN2212/GEN2212.asarr/PISCES_notebook/GridT/ORB1.nc'

Import the dataΒΆ

ds = xr.open_dataset(data_file)
ds
<xarray.Dataset>
Dimensions:               (axis_nbounds: 2, deptht: 31, tbnds: 2, time_counter: 12, x: 182, y: 149)
Coordinates:
  * time_counter          (time_counter) object 0000-01-16 00:00:00 ... 0000-...
    nav_lat               (y, x) float32 -78.19 -78.19 -78.19 ... 59.91 59.91
    nav_lon               (y, x) float32 105.0 107.0 109.0 ... 106.0 106.0 106.0
  * deptht                (deptht) float32 5.0 15.0 25.0 ... 4.75e+03 5.25e+03
    time_centered         (time_counter) object 7804-07-16 00:00:00 ... 7805-...
Dimensions without coordinates: axis_nbounds, tbnds, x, y
Data variables:
    time_counter_bnds     (time_counter, tbnds) object 0000-01-01 00:00:00 .....
    deptht_bounds         (deptht, axis_nbounds) float32 0.0 10.0 ... 5.501e+03
    time_centered_bounds  (time_counter, axis_nbounds) object 7804-07-01 00:0...
    time_counter_bounds   (time_counter, axis_nbounds) float64 1.837e+11 ... ...
    e3t                   (time_counter, deptht, y, x) float32 ...
    pbo                   (time_counter, y, x) float32 ...
    zos                   (time_counter, y, x) float32 ...
    zossq                 (time_counter, y, x) float32 ...
    thetao                (time_counter, deptht, y, x) float32 ...
    tos                   (time_counter, y, x) float32 ...
    tossq                 (time_counter, y, x) float32 ...
    so                    (time_counter, deptht, y, x) float32 ...
    sos                   (time_counter, y, x) float32 ...
    rhopoto               (time_counter, deptht, y, x) float32 ...
    omlmax                (time_counter, y, x) float32 ...
    mldkz5                (time_counter, y, x) float32 ...
    mldr10_1              (time_counter, y, x) float32 ...
    mldr10_1max           (time_counter, y, x) float32 ...
    wfcorr                (time_counter, y, x) float32 ...
    nshfls                (time_counter, y, x) float32 ...
    rsntds                (time_counter, y, x) float32 ...
    rsds                  (time_counter, deptht, y, x) float32 ...
    hfcorr                (time_counter, y, x) float32 ...
    mlddzt                (time_counter, y, x) float32 ...
    mldr10_3              (time_counter, y, x) float32 ...
    mldr0_1               (time_counter, y, x) float32 ...
    mldr0_3               (time_counter, y, x) float32 ...
    mld_dt02              (time_counter, y, x) float32 ...
    topthdep              (time_counter, y, x) float32 ...
    pycndep               (time_counter, y, x) float32 ...
    BLT                   (time_counter, y, x) float32 ...
    tinv                  (time_counter, y, x) float32 ...
    depti                 (time_counter, y, x) float32 ...
    hc300                 (time_counter, y, x) float32 ...
    hdivtr                (time_counter, deptht, y, x) float32 ...
    windsp                (time_counter, y, x) float32 ...
    wfob                  (time_counter, y, x) float32 ...
    fmmflx                (time_counter, y, x) float32 ...
    siconc                (time_counter, y, x) float32 ...
    sicover               (time_counter, y, x) float32 ...
    qt_oce                (time_counter, y, x) float32 ...
    qemp_oce              (time_counter, y, x) float32 ...
    qt_ice                (time_counter, y, x) float32 ...
    qemp_ice              (time_counter, y, x) float32 ...
    hflx_rain_cea         (time_counter, y, x) float32 ...
    hflx_evap_cea         (time_counter, y, x) float32 ...
    hflx_snow_cea         (time_counter, y, x) float32 ...
    hflx_cal_cea          (time_counter, y, x) float32 ...
    wfo                   (time_counter, y, x) float32 ...
    emp_oce               (time_counter, y, x) float32 ...
    emp_ice               (time_counter, y, x) float32 ...
    friver                (time_counter, y, x) float32 ...
    calving               (time_counter, y, x) float32 ...
    vfxice                (time_counter, y, x) float32 ...
    vfxsnw                (time_counter, y, x) float32 ...
    vfxsub                (time_counter, y, x) float32 ...
    vfxspr                (time_counter, y, x) float32 ...
    rain                  (time_counter, y, x) float32 ...
    snow_ao_cea           (time_counter, y, x) float32 ...
    snow_ai_cea           (time_counter, y, x) float32 ...
    evap_ao_cea           (time_counter, y, x) float32 ...
    subl_ai_cea           (time_counter, y, x) float32 ...
    sosflxdo              (time_counter, y, x) float32 ...
Attributes:
    name:                      CPL-90Ma-ORB1-TopoCorr_1m_grid_T
    description:               Created by xios
    title:                     Created by xios
    Conventions:               CF-1.6
    timeStamp:                 2020-Nov-07 22:04:10 GMT
    uuid:                      5a48fec9-7e00-46df-8ec8-5753a1e4a350
    LongName:                  restart from CPL-90Ma-BathyTotal for OCE/ICE/M...
    history:                   Mon Nov  9 05:21:33 2020: ncrcat -C --buffer_s...
    NCO:                       "4.6.0"
    nco_openmp_thread_number:  1

Setup the maskΒΆ

We need a mask for the convolution to know where the land is.

If we want ocean points then we set land to 1 and ocean 0 and the inverse if we want land points.

ds.pbo.hvplot.quadmesh(x='nav_lon', y='nav_lat', rasterize=True, geo=True, project=True)
vals = ds.pbo.isel(time_counter=0).values
hv.Image(vals).opts(tools=['hover'])
land = numpy.where(numpy.isnan(vals),1 ,0 )
hv.Image(land).opts(tools=['hover'])

ConvolutionΒΆ

We carry out a convolution. A convutlion is a moving mask that multiple the base values by template values.

As the land is 1 and ocean 0 we will only have values next to the land. We set the same value everywhere and positive inside the template.

template = numpy.array([[1, 1, 1], [1, 1, 1], [1, 1, 1]])
# Run convolution
convolution = convolve2d(land, template, 'same')

# Set land to 0
convolution = numpy.where(land, 0, convolution)

# Set all values now not null to 1
convolution[convolution > 0] = 1

hv.Image(convolution).opts(tools=['hover'])

Write mask back to datasetΒΆ

ds
<xarray.Dataset>
Dimensions:               (axis_nbounds: 2, deptht: 31, tbnds: 2, time_counter: 12, x: 182, y: 149)
Coordinates:
  * time_counter          (time_counter) object 0000-01-16 00:00:00 ... 0000-...
    nav_lat               (y, x) float32 -78.19 -78.19 -78.19 ... 59.91 59.91
    nav_lon               (y, x) float32 105.0 107.0 109.0 ... 106.0 106.0 106.0
  * deptht                (deptht) float32 5.0 15.0 25.0 ... 4.75e+03 5.25e+03
    time_centered         (time_counter) object 7804-07-16 00:00:00 ... 7805-...
Dimensions without coordinates: axis_nbounds, tbnds, x, y
Data variables:
    time_counter_bnds     (time_counter, tbnds) object 0000-01-01 00:00:00 .....
    deptht_bounds         (deptht, axis_nbounds) float32 0.0 10.0 ... 5.501e+03
    time_centered_bounds  (time_counter, axis_nbounds) object 7804-07-01 00:0...
    time_counter_bounds   (time_counter, axis_nbounds) float64 1.837e+11 ... ...
    e3t                   (time_counter, deptht, y, x) float32 ...
    pbo                   (time_counter, y, x) float32 ...
    zos                   (time_counter, y, x) float32 ...
    zossq                 (time_counter, y, x) float32 ...
    thetao                (time_counter, deptht, y, x) float32 ...
    tos                   (time_counter, y, x) float32 ...
    tossq                 (time_counter, y, x) float32 ...
    so                    (time_counter, deptht, y, x) float32 ...
    sos                   (time_counter, y, x) float32 ...
    rhopoto               (time_counter, deptht, y, x) float32 ...
    omlmax                (time_counter, y, x) float32 ...
    mldkz5                (time_counter, y, x) float32 ...
    mldr10_1              (time_counter, y, x) float32 ...
    mldr10_1max           (time_counter, y, x) float32 ...
    wfcorr                (time_counter, y, x) float32 ...
    nshfls                (time_counter, y, x) float32 ...
    rsntds                (time_counter, y, x) float32 ...
    rsds                  (time_counter, deptht, y, x) float32 ...
    hfcorr                (time_counter, y, x) float32 ...
    mlddzt                (time_counter, y, x) float32 ...
    mldr10_3              (time_counter, y, x) float32 ...
    mldr0_1               (time_counter, y, x) float32 ...
    mldr0_3               (time_counter, y, x) float32 ...
    mld_dt02              (time_counter, y, x) float32 ...
    topthdep              (time_counter, y, x) float32 ...
    pycndep               (time_counter, y, x) float32 ...
    BLT                   (time_counter, y, x) float32 ...
    tinv                  (time_counter, y, x) float32 ...
    depti                 (time_counter, y, x) float32 ...
    hc300                 (time_counter, y, x) float32 ...
    hdivtr                (time_counter, deptht, y, x) float32 ...
    windsp                (time_counter, y, x) float32 ...
    wfob                  (time_counter, y, x) float32 ...
    fmmflx                (time_counter, y, x) float32 ...
    siconc                (time_counter, y, x) float32 ...
    sicover               (time_counter, y, x) float32 ...
    qt_oce                (time_counter, y, x) float32 ...
    qemp_oce              (time_counter, y, x) float32 ...
    qt_ice                (time_counter, y, x) float32 ...
    qemp_ice              (time_counter, y, x) float32 ...
    hflx_rain_cea         (time_counter, y, x) float32 ...
    hflx_evap_cea         (time_counter, y, x) float32 ...
    hflx_snow_cea         (time_counter, y, x) float32 ...
    hflx_cal_cea          (time_counter, y, x) float32 ...
    wfo                   (time_counter, y, x) float32 ...
    emp_oce               (time_counter, y, x) float32 ...
    emp_ice               (time_counter, y, x) float32 ...
    friver                (time_counter, y, x) float32 ...
    calving               (time_counter, y, x) float32 ...
    vfxice                (time_counter, y, x) float32 ...
    vfxsnw                (time_counter, y, x) float32 ...
    vfxsub                (time_counter, y, x) float32 ...
    vfxspr                (time_counter, y, x) float32 ...
    rain                  (time_counter, y, x) float32 ...
    snow_ao_cea           (time_counter, y, x) float32 ...
    snow_ai_cea           (time_counter, y, x) float32 ...
    evap_ao_cea           (time_counter, y, x) float32 ...
    subl_ai_cea           (time_counter, y, x) float32 ...
    sosflxdo              (time_counter, y, x) float32 ...
Attributes:
    name:                      CPL-90Ma-ORB1-TopoCorr_1m_grid_T
    description:               Created by xios
    title:                     Created by xios
    Conventions:               CF-1.6
    timeStamp:                 2020-Nov-07 22:04:10 GMT
    uuid:                      5a48fec9-7e00-46df-8ec8-5753a1e4a350
    LongName:                  restart from CPL-90Ma-BathyTotal for OCE/ICE/M...
    history:                   Mon Nov  9 05:21:33 2020: ncrcat -C --buffer_s...
    NCO:                       "4.6.0"
    nco_openmp_thread_number:  1
ds['ocean_mask'] = ('y', 'x'), convolution
ds
<xarray.Dataset>
Dimensions:               (axis_nbounds: 2, deptht: 31, tbnds: 2, time_counter: 12, x: 182, y: 149)
Coordinates:
  * time_counter          (time_counter) object 0000-01-16 00:00:00 ... 0000-...
    nav_lat               (y, x) float32 -78.19 -78.19 -78.19 ... 59.91 59.91
    nav_lon               (y, x) float32 105.0 107.0 109.0 ... 106.0 106.0 106.0
  * deptht                (deptht) float32 5.0 15.0 25.0 ... 4.75e+03 5.25e+03
    time_centered         (time_counter) object 7804-07-16 00:00:00 ... 7805-...
Dimensions without coordinates: axis_nbounds, tbnds, x, y
Data variables:
    time_counter_bnds     (time_counter, tbnds) object 0000-01-01 00:00:00 .....
    deptht_bounds         (deptht, axis_nbounds) float32 0.0 10.0 ... 5.501e+03
    time_centered_bounds  (time_counter, axis_nbounds) object 7804-07-01 00:0...
    time_counter_bounds   (time_counter, axis_nbounds) float64 1.837e+11 ... ...
    e3t                   (time_counter, deptht, y, x) float32 ...
    pbo                   (time_counter, y, x) float32 ...
    zos                   (time_counter, y, x) float32 ...
    zossq                 (time_counter, y, x) float32 ...
    thetao                (time_counter, deptht, y, x) float32 ...
    tos                   (time_counter, y, x) float32 ...
    tossq                 (time_counter, y, x) float32 ...
    so                    (time_counter, deptht, y, x) float32 ...
    sos                   (time_counter, y, x) float32 ...
    rhopoto               (time_counter, deptht, y, x) float32 ...
    omlmax                (time_counter, y, x) float32 ...
    mldkz5                (time_counter, y, x) float32 ...
    mldr10_1              (time_counter, y, x) float32 ...
    mldr10_1max           (time_counter, y, x) float32 ...
    wfcorr                (time_counter, y, x) float32 ...
    nshfls                (time_counter, y, x) float32 ...
    rsntds                (time_counter, y, x) float32 ...
    rsds                  (time_counter, deptht, y, x) float32 ...
    hfcorr                (time_counter, y, x) float32 ...
    mlddzt                (time_counter, y, x) float32 ...
    mldr10_3              (time_counter, y, x) float32 ...
    mldr0_1               (time_counter, y, x) float32 ...
    mldr0_3               (time_counter, y, x) float32 ...
    mld_dt02              (time_counter, y, x) float32 ...
    topthdep              (time_counter, y, x) float32 ...
    pycndep               (time_counter, y, x) float32 ...
    BLT                   (time_counter, y, x) float32 ...
    tinv                  (time_counter, y, x) float32 ...
    depti                 (time_counter, y, x) float32 ...
    hc300                 (time_counter, y, x) float32 ...
    hdivtr                (time_counter, deptht, y, x) float32 ...
    windsp                (time_counter, y, x) float32 ...
    wfob                  (time_counter, y, x) float32 ...
    fmmflx                (time_counter, y, x) float32 ...
    siconc                (time_counter, y, x) float32 ...
    sicover               (time_counter, y, x) float32 ...
    qt_oce                (time_counter, y, x) float32 ...
    qemp_oce              (time_counter, y, x) float32 ...
    qt_ice                (time_counter, y, x) float32 ...
    qemp_ice              (time_counter, y, x) float32 ...
    hflx_rain_cea         (time_counter, y, x) float32 ...
    hflx_evap_cea         (time_counter, y, x) float32 ...
    hflx_snow_cea         (time_counter, y, x) float32 ...
    hflx_cal_cea          (time_counter, y, x) float32 ...
    wfo                   (time_counter, y, x) float32 ...
    emp_oce               (time_counter, y, x) float32 ...
    emp_ice               (time_counter, y, x) float32 ...
    friver                (time_counter, y, x) float32 ...
    calving               (time_counter, y, x) float32 ...
    vfxice                (time_counter, y, x) float32 ...
    vfxsnw                (time_counter, y, x) float32 ...
    vfxsub                (time_counter, y, x) float32 ...
    vfxspr                (time_counter, y, x) float32 ...
    rain                  (time_counter, y, x) float32 ...
    snow_ao_cea           (time_counter, y, x) float32 ...
    snow_ai_cea           (time_counter, y, x) float32 ...
    evap_ao_cea           (time_counter, y, x) float32 ...
    subl_ai_cea           (time_counter, y, x) float32 ...
    sosflxdo              (time_counter, y, x) float32 ...
    ocean_mask            (y, x) int64 0 0 0 0 0 0 0 0 0 0 ... 0 0 0 0 0 0 0 0 0
Attributes:
    name:                      CPL-90Ma-ORB1-TopoCorr_1m_grid_T
    description:               Created by xios
    title:                     Created by xios
    Conventions:               CF-1.6
    timeStamp:                 2020-Nov-07 22:04:10 GMT
    uuid:                      5a48fec9-7e00-46df-8ec8-5753a1e4a350
    LongName:                  restart from CPL-90Ma-BathyTotal for OCE/ICE/M...
    history:                   Mon Nov  9 05:21:33 2020: ncrcat -C --buffer_s...
    NCO:                       "4.6.0"
    nco_openmp_thread_number:  1
ds['ocean_mask'].hvplot.quadmesh(x='nav_lon', y='nav_lat', cmap='viridis')