Unidata / MetPy

MetPy is a collection of tools in Python for reading, visualizing and performing calculations with weather data.
https://unidata.github.io/MetPy/
BSD 3-Clause "New" or "Revised" License
1.26k stars 415 forks source link

Laplacian based on finite difference vs spectral technique #3458

Open ahmedshaaban1 opened 8 months ago

ahmedshaaban1 commented 8 months ago

All, As Laplacian could be computed using finite difference techniques (e.g., second derivative or first derivative of the first derivative ) or spectral methods, It will be helpful to mention the technique used in calculating the Laplacian in the function's documentation section.

Another thing, I calculated the Laplacian of the ERA5 500 hPa geopotential height using NCL (which uses spectral technique) and MetPy (which uses the second derivative). Laplacian based on spectral technique (figure on the left) is too noisy and, at the same time, richer in detail than that based on the finite difference (figure on the right). I don't know if both figures are comparable. Given such differences, any idea on which technique should be adopted for calculating geophysical fields (e.g., vorticity from Laplacian of the geopotential). Below is the ERA5 500 hPa vorticity downloaded from the Copernicus data center; vorticity shares some patterns with the Laplacian based on the spectral technique, except it is not too noisy. Please remember that vorticity is associated with the Laplacian of the geostrophic height.

Here is the Python code used to calculate the Laplacian.

import matplotlib.pyplot as plt
import xarray as xr
import py4met as p4m
import py4plot as p4p
import metpy.calc as mpcalc

#%% opening the dataset 
diri   ="./"
myfile   = xr.open_dataset(diri+"vor_geo_era5_2023_jan.nc")
var_z_pre    = myfile['z']   # geopotential m**2 S**-2
var_vo_pre  = myfile['vo']   # relative vorticity s**-1

timeP     = myfile['time']
lonP      = myfile['longitude'].data
latPP     = myfile['latitude'].data
myfile 

myfile
var_z=var_z_pre*1.
var_vo=var_vo_pre*1.
lap = mpcalc.laplacian(var_z[:,:,:],axes=('latitude','longitude'))

here is the NCL code used to calculate the Laplacian

load "$NCARG_ROOT/lib/ncarg/nclscripts/csm/gsn_code.ncl"
load "$NCARG_ROOT/lib/ncarg/nclscripts/csm/gsn_csm.ncl"
begin
   diri   ="/"
   a = addfile(diri+"vor_geo_era5_2023_jan.nc","r")
   ght = a->z(:,:,:)
   vor = a->vo(:,:,:)
   print(ght(0,80:,:))

   lapl = lapsF(ght(:,::-1,:)) ; ascending latitude order
   temp     = addfile(diri+"lap_ght_calculated_era5.nc" ,"c")  ; open output netCDF file
   temp->lapl   = lapl
end

Here is the link for the netcdf files lap_ght_calculated_era5.nc vor_geo_era5_2023_jan.nc Thanks

out vorticity

dopplershift commented 8 months ago

Would be happy to accept a PR that includes a specific mention of the use of finite differencing in the docs for laplacian and geospatial_laplacian.

As far as which one is more appropriate, unfortunately that's beyond my area of expertise.