Skip to content

Commit

Permalink
Merge dccd00a into 4a0167e
Browse files Browse the repository at this point in the history
  • Loading branch information
wpreimes committed May 23, 2019
2 parents 4a0167e + dccd00a commit 7c9646f
Show file tree
Hide file tree
Showing 5 changed files with 55 additions and 45 deletions.
5 changes: 3 additions & 2 deletions .travis.yml
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
dist: xenial
language: python
sudo: false
addons:
Expand All @@ -10,8 +11,8 @@ notifications:
python:
# We don't actually use the Travis Python, but this keeps it organized.
- "2.7"
- "3.4"
- "3.5"
- "3.6"
- "3.7"
install:
# You may want to periodically update this, although the conda update
# conda line below will keep everything up-to-date. We do this
Expand Down
7 changes: 6 additions & 1 deletion CHANGES.rst
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,12 @@
Changelog
=========

Version 0.X
Unreleased
==========

- Add gldas land mask to package (no download necessary)

Version 0.5
===========

- Update trollsift parsing
Expand Down
Binary file added gldas/GLDASp4_landmask_025d.nc4
Binary file not shown.
76 changes: 42 additions & 34 deletions gldas/grid.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,47 +23,55 @@
import numpy as np

from pygeogrids.grids import BasicGrid
import pandas as pd
from netCDF4 import Dataset
import os


def GLDAS025Cellgrid():
'''
GLDAS-Noah 0.25deg cell grid.
:return: global QDEG-CellGrid
'''
def GLDAS025Grids(only_land=False):
"""
Create global 0.25 DEG gldas grids (origin in bottom left)
Parameters
---------
only_land : bool, optional (default: False)
Uses the land mask to reduce the GLDAS 0.25DEG land grid to land points
only.
Returns
--------
grid : pygeogrids.CellGrid
Either a land grid or a global grid
"""

resolution = 0.25
lon, lat = np.meshgrid(
np.arange(-180 + resolution / 2, 180 + resolution / 2, resolution),
np.arange(-90 + resolution / 2, 90 + resolution / 2, resolution))
glob_lons = np.arange(-180 + resolution / 2, 180 + resolution / 2, resolution)
glob_lats = np.arange(-90 + resolution / 2, 90 + resolution / 2, resolution)
lon, lat = np.meshgrid(glob_lons, glob_lats)
glob_grid = BasicGrid(lon.flatten(), lat.flatten()).to_cell_grid(cellsize=5.)

return BasicGrid(lon.flatten(), lat.flatten()).to_cell_grid(cellsize=5.)
if only_land:
ds = Dataset(os.path.join(os.path.abspath(os.path.dirname(__file__)),
'GLDASp4_landmask_025d.nc4'))
land_lats = ds.variables['lat'][:]
land_mask = ds.variables['GLDAS_mask'][:].flatten().filled() == 0.
dlat = glob_lats.size - land_lats.size

land_mask = np.concatenate((np.ones(dlat * glob_lons.size), land_mask))
land_points = np.ma.masked_array(glob_grid.get_grid_points()[0], land_mask)

def GLDASLandPoints(grid):
'''
Load land mask from https://ldas.gsfc.nasa.gov/gldas/data/0.25deg/landmask_mod44w_025.asc
and reduce input grid to land points
:return: (GPI, dist)
'''
try:
land_mask = pd.read_csv('https://ldas.gsfc.nasa.gov/gldas/data/0.25deg/landmask_mod44w_025.asc',
delim_whitespace=True, header=None, names=['idx', 'gpi', 'lat', 'lon', 'land_flag'])
except:
raise ImportError(
'reading land mask from https://ldas.gsfc.nasa.gov/gldas/data/0.25deg/landmask_mod44w_025.asc failed.')
land_mask = land_mask.loc[land_mask['land_flag'] == 1]
lat, lon = land_mask['lat'].values, land_mask['lon'].values
land_grid = glob_grid.subgrid_from_gpis(land_points[~land_points.mask].filled())
return land_grid
else:
return glob_grid

return grid.find_nearest_gpi(lon, lat)

def GLDAS025Cellgrid():
return GLDAS025Grids(only_land=False)


def GLDAS025LandGrid():
'''
0.25deg cell grid of land points from gldas land mask.
:return: global QDEG-LandGrid
'''
grid = GLDAS025Cellgrid()
land_gpis, dist = GLDASLandPoints(grid)
if any(dist) > 0:
raise Exception('GLDAS grid does not conform with QDEG grid')
return grid.subgrid_from_gpis(land_gpis)
return GLDAS025Grids(only_land=True)


if __name__ == '__main__':
GLDAS025LandGrid()
12 changes: 4 additions & 8 deletions gldas/interface.py
Original file line number Diff line number Diff line change
Expand Up @@ -60,8 +60,7 @@ class GLDAS_Noah_v21_025Img(ImageBase):
Needed for some legacy code.
"""


def __init__(self, filename, mode='r', parameter='SoilMoi0_10cm_inst',
def __init__(self, filename, mode='r', parameter='SoilMoi0_10cm_inst',
subgrid=None, array_1D=False):

super(GLDAS_Noah_v21_025Img, self).__init__(filename, mode=mode)
Expand Down Expand Up @@ -107,7 +106,7 @@ def read(self, timestamp=None):
np.ma.set_fill_value(param_data, 9999)
param_data = np.concatenate((
self.fill_values,
np.ma.getdata(param_data.filled()) .flatten()))
np.ma.getdata(param_data.filled()).flatten()))

return_img.update(
{str(parameter): param_data[self.grid.activegpis]})
Expand All @@ -130,13 +129,12 @@ def read(self, timestamp=None):

if self.array_1D:
return Image(self.grid.activearrlon, self.grid.activearrlat,
return_img, return_metadata, timestamp)
return_img, return_metadata, timestamp)
else:
for key in return_img:
return_img[key] = np.flipud(
return_img[key].reshape((720, 1440)))


return Image(np.flipud(self.grid.activearrlon.reshape((720, 1440))),
np.flipud(self.grid.activearrlat.reshape((720, 1440))),
return_img,
Expand Down Expand Up @@ -292,9 +290,8 @@ class GLDAS_Noah_v21_025Ds(MultiTemporalImageBase):
Needed for some legacy code.
"""

def __init__(self, data_path, parameter='SoilMoi0_10cm_inst',
def __init__(self, data_path, parameter='SoilMoi0_10cm_inst',
subgrid=None, array_1D=False):

ioclass_kws = {'parameter': parameter,
'subgrid': subgrid,
'array_1D': array_1D}
Expand All @@ -309,7 +306,6 @@ def __init__(self, data_path, parameter='SoilMoi0_10cm_inst',
exact_templ=False,
ioclass_kws=ioclass_kws)


def tstamps_for_daterange(self, start_date, end_date):
"""
return timestamps for daterange,
Expand Down

0 comments on commit 7c9646f

Please sign in to comment.