Skip to content

Commit 907bb50

Browse files
authored
Merge pull request #12 from stephenworsley/regridding_fixes
Address additional comments for regridding section
2 parents 3446bcd + aa93e71 commit 907bb50

File tree

2 files changed

+316
-159
lines changed

2 files changed

+316
-159
lines changed

notebooks/.notebook_shadow_copies/Sec_05_Regridding.md

Lines changed: 43 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -17,12 +17,7 @@ jupyter:
1717
## Set up
1818

1919
```python
20-
from pathlib import Path
21-
import numpy as np
22-
2320
from esmf_regrid.experimental.unstructured_scheme import MeshToGridESMFRegridder, GridToMeshESMFRegridder
24-
import iris
25-
from iris import load, load_cube
2621
from iris.coords import DimCoord
2722
from iris.cube import Cube
2823
```
@@ -104,6 +99,7 @@ import matplotlib.pyplot as plt
10499
from testdata_fetching import um_temp
105100
grid_temp = um_temp()
106101

102+
# We slice the cube to make sure it is 2D for plotting.
107103
iqplt.pcolormesh(grid_temp[0, 0])
108104
plt.gca().coastlines()
109105
plt.show()
@@ -113,11 +109,12 @@ plt.gca().coastlines()
113109
plt.show()
114110
```
115111

116-
We can then plot the difference between the UM data and the data regridded from LFRic. Since our data is now on a latlon grid we can do this with matplotlib as normal.
112+
We can then plot the difference between the UM data and the data regridded from LFRic. Since all our data is now on a latlon grid we can subtract to find the difference between the regridded LFRic data and equivalent UM data and plot this with matplotlib as normal.
117113

118114
```python
119115
temp_diff = result_2 - grid_temp
120116

117+
# We choose a colormap that makes it clear where the differences are.
121118
iqplt.pcolormesh(temp_diff[0, 0], vmin=-4,vmax=4, cmap="seismic")
122119
plt.gca().coastlines()
123120
plt.show()
@@ -206,10 +203,10 @@ lat_bands = DimCoord(
206203
lon_full = DimCoord(0, bounds=[[-180, 180]], standard_name="longitude", units="degrees")
207204
```
208205

209-
**Step 3:** Create a single celled cube (i.e. `Cube([[0]])`) and attach the latitude and longitude coordinates to it.
206+
**Step 3:** Create a six celled cube (i.e. `Cube([[0, 0, 0, 0, 0, 0]])`) and attach the latitude and longitude coordinates to it.
210207

211208
```python
212-
lat_band_cube = Cube(np.zeros((1,) + lat_bands.shape))
209+
lat_band_cube = Cube([[0, 0, 0, 0, 0, 0]])
213210
lat_band_cube.add_dim_coord(lat_bands, 1)
214211
lat_band_cube.add_dim_coord(lon_full, 0)
215212
lat_band_cube
@@ -227,7 +224,7 @@ Initialise a `MeshToGridESMFRegridder` with `mesh_cube` and your single celled c
227224
lat_band_mean_calculator_10 = MeshToGridESMFRegridder(mesh_cube, lat_band_cube, resolution=10)
228225
```
229226

230-
**Step 5:** Apply this regridder to `mesh_cube` and print the data from this result (i.e. `print(result_cube.data)`).
227+
**Step 5:** Apply this regridder to `mesh_cube` and print the data from this result (i.e. `print(result_cube.data)`) and plot with `iqplt.pcolormesh`.
231228

232229
```python
233230
lat_band_mean_10 = lat_band_mean_calculator_10(mesh_cube)
@@ -239,7 +236,7 @@ plt.show()
239236

240237
**Step 6:** Repeat step 4 and 5 for `resolution=100`.
241238

242-
Note the difference in value. Also note that it takes more time to initialise a regridder with higher resolution.
239+
Note the difference in value. Also note that it takes more time to initialise a regridder with higher resolution. Higher resolutions ought to be more accurate but there is a tradeoff between performance and accuracy.
243240

244241
```python
245242
lat_band_mean_calculator_100 = MeshToGridESMFRegridder(mesh_cube, lat_band_cube, resolution=100)
@@ -274,64 +271,68 @@ print(lon_band_mean_10.data)
274271

275272
## Exercise 3: Hovmoller plots
276273

277-
If we have data on aditional dimensions, we can use the same approach as exercise 2 to produce a Hovmoller diagram. That is, if we have data that varies along time we can take the area weighted mean over latitude bands and plot the data aginst longitude and time (or similarly, we can plot against latitude and time).
278-
279-
**Step 1:** Load a temperature cube using the `testdata_fetching` function `lfric_temp`. Extract a single pressure slice using the `cube.extract` method with a constraint `iris.Constraint(pressure=850)` as the argument (we choose this level because it has noticable details).
274+
If we have data on aditional dimensions, we can use the same approach as exercise 2 to produce a Hovmoller diagram. That is, if we have data that varies along time we can take the area weighted mean over latitude bands and plot the data aginst latitude and time (or similarly, we can plot against longitude and time).
280275

276+
**Step 1:** Load a cube with humidity data using the `testdata_fetching` function `lfric_rh_alltimes_3d`.
281277

282-
from testdata_fetching import fric_temp
283-
mesh_temp = lfric_temp()
284-
285-
temp_slice = mesh_temp.extract(iris.Constraint(pressure=850))
286-
temp_slice
278+
```python
279+
from testdata_fetching import lfric_rh_alltimes_3d
287280

281+
humidity_cube = lfric_rh_alltimes_3d()
282+
humidity_cube
283+
```
288284

289-
**Step 2:** Create a target cube whose longitude coordinate is derived from the UM cube loaded from `um_orography` and whose latitude coordinate has bounds `[[-180, 180]]`. This can be done by slicing a cube derived from `um_orography` (using the slice `[:1]` so that this dimension isnt collapsed), removing the latitude coordinate and adding a latitude coordinate with bounds `[[-180, 180]]` (you can reuse the coordinate from exercise 2).
285+
**Step 2:** Create a target cube whose latitude coordinate is derived from the UM cube loaded from `um_orography` and whose longitude coordinate has bounds `[[-180, 180]]`. This can be done by slicing a cube derived from `um_orography` (using the slice `[:, :1]` so that this dimension isnt collapsed), removing the longitude coordinate and adding a longitude coordinate with bounds `[[-180, 180]]` (you can reuse the coordinate from exercise 2).
290286

291287
```python
292-
target_cube_lons = grid_cube[:1]
293-
target_cube_lons.remove_coord("latitude")
294-
target_cube_lons.add_dim_coord(lat_full, 0)
295-
target_cube_lons
288+
target_cube_lats = grid_cube[:,:1]
289+
target_cube_lats.remove_coord("longitude")
290+
target_cube_lats.add_dim_coord(lon_full, 1)
291+
target_cube_lats
296292
```
297293

298294
```python
299-
# We also can do the same thing for bands of constant latitude.
295+
# We also can do the same thing for bands of constant longitude.
300296

301-
# target_cube_lats = grid_cube[:,:1]
302-
# target_cube_lats.remove_coord("longitude")
303-
# target_cube_lats.add_dim_coord(lon_full, 1)
304-
# target_cube_lats
297+
# target_cube_lons = grid_cube[:1]
298+
# target_cube_lons.remove_coord("latitude")
299+
# target_cube_lons.add_dim_coord(lat_full, 0)
300+
# target_cube_lons
305301
```
306302

307-
**Step 3:** Create a `MeshToGridESMFRegridder` regridder from the slice of the temperature cube onto the target cube. Set the resolution keyword to 2 (this should be sufficient since these are bands of constant longitude). Use this regridder to create a resulting cube.
303+
**Step 3:** Create a `MeshToGridESMFRegridder` regridder from the slice of the humidity cube onto the target cube. Set the resolution keyword to 500 (this should be good balance of accuracy and performance). Use this regridder to create a resulting cube.
308304

309305
```python
310-
um_lon_band_mean_calculator = MeshToGridESMFRegridder(temp_slice, target_cube_lons, resolution=2)
311-
um_lon_bound_means = um_lon_band_mean_calculator(temp_slice)
312-
um_lon_bound_means
306+
um_lat_band_mean_calculator = MeshToGridESMFRegridder(humidity_cube, target_cube_lats, resolution=500)
307+
um_lat_band_means = um_lat_band_mean_calculator(humidity_cube)
308+
um_lat_band_means
313309
```
314310

315311
```python
316-
# um_lat_band_mean_calculator = MeshToGridESMFRegridder(temp_slice, target_cube, resolution=500)
317-
# um_lat_bound_means = um_lat_band_mean_calculator(temp_slice)
318-
# um_lat_bound_means
312+
# Continuing for bands of constant longitude.
313+
# Note: this code takes about 2 minutes to run. I think this is due to with the way ESMF handles cells
314+
# with unusual shapes. See https://github.com/SciTools-incubator/iris-esmf-regrid/issues/234.
315+
316+
# um_lon_band_mean_calculator = MeshToGridESMFRegridder(humidity_cube, target_cube_lons, resolution=2)
317+
# um_lon_band_means = um_lon_band_mean_calculator(humidity_cube)
318+
# um_lon_band_means
319319
```
320320

321-
**Step 4:** Plot the data in the resulting cube. This can be done with `iqplt.pcolormesh`. Note that the resulting cube will have an unnecessary dimension which will have to be sliced (using `[:, 0]`). Note that extra steps can be taken to format the dates for this plot.
321+
**Step 4:** Plot the data in the resulting cube. This can be done with `iqplt.pcolormesh`. Note that the resulting cube will have an unnecessary dimension which will have to be sliced (using `[:, :, 0]`). Note that extra steps can be taken to format the dates for this plot.
322322

323323
```python
324324
import matplotlib.dates as mdates
325-
326-
iqplt.pcolormesh(um_lon_bound_means[:, 0, :])
327-
plt.gca().yaxis.set_major_formatter(mdates.DateFormatter("%D"))
325+
# We use a colormap which highlights fine details.
326+
iqplt.pcolormesh(um_lat_band_means[:, :, 0])
327+
plt.gca().xaxis.set_major_formatter(mdates.DateFormatter("%D"))
328328
plt.show()
329329
```
330330

331331
```python
332-
# import matplotlib.dates as mdates
333-
# iqplt.pcolormesh(um_lat_bound_means[:, :, 0])
334-
# plt.gca().xaxis.set_major_formatter(mdates.DateFormatter("%D"))
332+
# Continuing for bands of constant longitude.
333+
334+
# iqplt.pcolormesh(um_lon_band_means[:, 0])
335+
# plt.gca().yaxis.set_major_formatter(mdates.DateFormatter("%D"))
335336
# plt.show()
336337
```
337338

@@ -342,7 +343,3 @@ plt.show()
342343
# Use this regridder to compare how well bilinear regridding and area weighted
343344
# regridding preserve area weighted mean after round tripping.
344345
```
345-
346-
```python
347-
348-
```

0 commit comments

Comments
 (0)