This recipe shows how to calculate a depth-time Hovmoller plot of 1-year anomaly of annual, globally-averaged anomalies of conservative temperature from ACCESS-OM2 between Jan 1989 and Dec 2018.
/g/data/xp65/public/apps/med_conda/envs/analysis3-26.05/lib/python3.12/site-packages/distributed/node.py:188: UserWarning: Port 8787 is already in use.
Perhaps you already have a cluster running?
Hosting the HTTP server on port 36141 instead
warnings.warn(
Next, we load cell area (denoted as \(a(x,y,z)\)) to construct the total ocean area as a function of depth, \(A\), namely
\[A(z) = \sum_x \sum_y a(x,y,z)\]
We load dxt and dyt and compute a masked version of cell area; we also use a slight hack to divide temperature by itself and thereby get a 3-dimensional cell area mask that is needed to create \(A(z)\). Note that we need the correct area sum at each depth that accounts for the depth-varying land mask.
[7]:
cat_subset=catalog.search(name=experiment)cell_area=cat_subset[experiment].search(variable='area_t',frequency='fx',path=".*output000.*").to_dask()['area_t']## Make a mask to get vertical variation of areatemp1=temperature.isel(time=0)cell_mask=temp1/temp1total_area=(cell_area*cell_mask).sum({'xt_ocean','yt_ocean'}).load()
Now, the mean temperature at each time level can then be computed as
where \(T\) is the globally average temperature anomaly and \(\tilde{\theta}\) is conservative temperature.
[ ]:
### Temperature hovmollertemperature_hov=(cell_area*temperature_anomaly).sum({'xt_ocean','yt_ocean'})/total_areatemperature_hov=temperature_hov.compute()
[ ]:
defplot_hovmoller(fsize=14,date_format=mdates.DateFormatter('%Y')):# Set figures propertiesplt.rcParams['font.size']=fsizeplt.rcParams['xtick.labelsize']=fsize-2plt.rcParams['ytick.labelsize']=fsize-2fig=plt.figure(figsize=(10,6))grid=GridSpec(100,100)ax=[fig.add_subplot(grid[:30,:]),fig.add_subplot(grid[32:,:])]foriinrange(len(ax)):ax[i].xaxis.set_major_formatter(date_format)ax[i].tick_params(axis='x',labelrotation=45)returnfig,ax
[ ]:
fig,ax=plot_hovmoller(fsize=14)levels_temperature=np.arange(-0.3,0.31,0.01)shelf_temp=temperature_hov.plot(ax=ax[0],levels=levels_temperature,x='time',y='st_ocean',add_colorbar=False,label=None,cmap=cm.balance)temperature_hov.plot(ax=ax[1],levels=levels_temperature,x='time',y='st_ocean',add_colorbar=False,label=None,cmap=cm.balance)## Beautification detailsax[0].set_ylim(500,0)ax[0].set_ylabel("")ax[0].set_xlabel("")ax[0].set_xticklabels([])ax[1].set_ylabel("Depth [m]",loc="top")ax[1].set_ylim(5000,500)ax[1].set_xlabel("")# or ax[1].set_xlabel("Time")# Colorbarsbar=plt.axes([0.13,0.99,0.77,0.03])cbar_1=plt.colorbar(shelf_temp,cax=bar,orientation='horizontal',extend='both',format='%.2f')cbar_1.set_label("Temperature [$\degree$C]")forcbarin[cbar_1]:tick_locator=ticker.MaxNLocator(nbins=5)## The ticker needs to called within the loopcbar.locator=tick_locatorcbar.update_ticks()