def read(self): # reading canal supply: if self.include_canal_system: if self.VariableCanalSupply: if self.DailyCanalNC: # introduce this test so that we do not ask the model to read # a file from a timestep prior to the current simulation. if not (self._modelTime.isFirstTimestep() & (self.canalTimeLag > 0)): day, month, year = self._modelTime.day, self._modelTime.month, self._modelTime.year canalFileNC = self.canalFileNC.format(day=day, month=month, year=year) exists = os.path.exists(canalFileNC) max_wait_time = 60 wait_time = 0.1 total_wait_time = 0 while exists is False and total_wait_time <= max_wait_time: time.sleep(wait_time) exists = os.path.exists(canalFileNC) total_wait_time += wait_time if not exists: msg = "canal file doesn't exist and maximum wait time exceeded" raise AQError(msg) CanalSupply = vos.netcdf2PCRobjCloneWithoutTime( canalFileNC, self.canalVarName, cloneMapFileName=self.cloneMap, LatitudeLongitude=True) self.CanalSupply = CanalSupply[self.landmask] else: CanalSupply = vos.netcdf2PCRobjClone( self.canalFileNC, self.canalVarName, str(currTimeStep.fulldate), useDoy=method_for_time_index, cloneMapFileName=self.cloneMap, LatitudeLongitude=True) self.CanalSupply = CanalSupply[self.landmask] else: CanalSupply = vos.netcdf2PCRobjCloneWithoutTime( self.canalFileNC, self.canalVarName, cloneMapFileName=self.cloneMap, LatitudeLongitude=True) self.CanalSupply = CanalSupply[self.landmask]
def read_root_fraction(self): landmask = np.broadcast_to(self.var.landmask, (2, self.var.nLat, self.var.nLon)) root_fraction = vos.netcdf2PCRobjCloneWithoutTime( self.rootFractionNC, self.rootFractionVarName, cloneMapFileName=self.var.cloneMap) root_fraction = root_fraction[landmask].reshape(2, self.var.nCell) root_fraction = np.broadcast_to( root_fraction[None, None, :, :], (self.var.nFarm, self.var.nCrop, 2, self.var.nCell)) # scale root fraction - adapted from CWATM # landcoverType.py lines 311-319 # 1 - add top layer to root fraction input data root_fraction_adj = np.zeros( (self.var.nFarm, self.var.nCrop, self.var.nLayer, self.var.nCell)) top_layer_fraction = np.divide( self.var.root_depth[..., 0, :], (self.var.root_depth[..., 0, :] + self.var.root_depth[..., 1, :])) root_fraction_adj[..., 0, :] = top_layer_fraction * root_fraction[..., 0, :] root_fraction_adj[ ..., 1, :] = (1. - top_layer_fraction) * root_fraction[..., 1, :] root_fraction_adj[..., 2, :] = (1. - root_fraction[..., 1, :]) # 2 - scale so that the total root fraction sums to one root_fraction_sum = np.sum(root_fraction_adj, axis=-2) root_fraction_adj /= root_fraction_sum[..., None, :] self.var.root_fraction = root_fraction_adj.copy()
def initial(self): self.var.irrMgmtParameterFileNC = self.var._configuration.irrMgmtOptions[ 'irrMgmtParameterNC'] self.var.parameter_names = [ 'IrrMethod', 'IrrInterval', 'SMT1', 'SMT2', 'SMT3', 'SMT4', 'MaxIrr', 'AppEff', 'NetIrrSMT', 'WetSurf' ] for param in self.var.parameter_names: # nm = '_' + var vars(self.var)[param] = vos.netcdf2PCRobjCloneWithoutTime( self.var.irrMgmtParameterFileNC, param, cloneMapFileName=self.var.cloneMap) # check if an irrigation schedule file is required if np.sum(self.var.IrrMethod == 3) > 0: if self.var._configuration.irrMgmtOptions[ 'irrScheduleNC'] != "None": self.var._configuration.irrMgmtOptions[ 'irrScheduleNC'] = vos.getFullPath( self.var._configuration.irrMgmtOptions[item], self.var._configuration.globalOptions['inputDir']) self.var.irrScheduleFileNC = self.var._configuration.irrMgmtOptions[ 'irrScheduleNC'] else: logger.error( 'IrrMethod equals 3 in some or all places, but irrScheduleNC is not set in configuration file' ) else: self.var.irrScheduleFileNC = None
def initial(self): self.WaterTable = bool( int(self._configuration.GROUNDWATER['WaterTable'])) self.VariableWaterTable = bool( int(self._configuration.GROUNDWATER['VariableWaterTable'])) self.DailyGroundwaterNC = bool( int(self._configuration.GROUNDWATER['DailyGroundwaterInputFile'])) zGW = np.ones_like(self.landmask) * 999. self.zGW = zGW[self.landmask] # self.zGW = np.ones((self.nCell)) * 999. if self.WaterTable: self.gwFileNC = self._configuration.GROUNDWATER[ 'groundwaterInputFile'] self.gwVarName = self._configuration.GROUNDWATER[ 'groundwaterVariableName'] self.gwTimeLag = int(self._configuration.GROUNDWATER['timeLag']) # if the program is configured to read daily groundwater files and # the time lag is positive, we also need to read an initial value # file if self.DailyGroundwaterNC & (self.gwTimeLag > 0): initialGroundwaterLevelNC = str( self._configuration. INITIAL_CONDITIONS['initialGroundwaterLevelInputFile']) zGW = vos.netcdf2PCRobjCloneWithoutTime( initialGroundwaterLevelNC, self.gwVarName, cloneMapFileName=self.cloneMap, LatitudeLongitude=True) self.zGW = zGW[self.landmask]
def read(self): relative_elevation_var_names = [ 'dzRel0001', 'dzRel0005', 'dzRel0010', 'dzRel0020', 'dzRel0030', 'dzRel0040', 'dzRel0050', 'dzRel0060', 'dzRel0070', 'dzRel0080', 'dzRel0090', 'dzRel0100' ] for var_name in relative_elevation_var_names: d = vos.netcdf2PCRobjCloneWithoutTime( str(self.lc_configuration['relativeElevationInputFile']), var_name, cloneMapFileName=self.var.cloneMap)[self.var.landmask] vars(self.var)[var_name] = d self.var.elevation_standard_deviation = vos.netcdf2PCRobjCloneWithoutTime( str(self.lc_configuration['elevationStandardDeviationInputFile']), 'dem_standard_deviation', cloneMapFileName=self.var.cloneMap)[self.var.landmask]
def read(self): """Function to read crop input parameters""" if len(self.var.crop_parameters_to_read) > 0: for param in self.var.crop_parameters_to_read: # nm = '_' + param vars(self.var)[param] = vos.netcdf2PCRobjCloneWithoutTime( self.var.cropParameterFileNC, param, cloneMapFileName=self.var.cloneMap)
def initial(self): self.var.fieldMgmtParameterFileNC = self.var._configuration.fieldMgmtOptions['fieldMgmtParameterNC'] self.var.parameter_names = ['Mulches','MulchPctGS','MulchPctOS','fMulch','Bunds','zBund','BundWater'] for var in self.var.parameter_names: # nm = '_' + var vars(self.var)[var] = vos.netcdf2PCRobjCloneWithoutTime( self.var.fieldMgmtParameterFileNC, var, cloneMapFileName=self.var.cloneMap)
def read_max_root_depth(self): max_root_depth = vos.netcdf2PCRobjCloneWithoutTime( self.maxRootDepthNC, self.maxRootDepthVarName, cloneMapFileName=self.var.cloneMap) # nlat, nlon max_root_depth = max_root_depth[self.var.landmask] max_root_depth *= self.var.soildepth_factor # CALIBRATION self.var.max_root_depth = np.broadcast_to( max_root_depth[None, None, :], (self.var.nFarm, self.var.nCrop, self.var.nCell))
def read(self): """Function to read crop input parameters""" if len(self.crop_parameters_to_read) > 0: for param in self.crop_parameters_to_read: d = vos.netcdf2PCRobjCloneWithoutTime( self.CropParameterNC, param, cloneMapFileName=self.var.cloneMap) d = d[self.var.landmask_crop].reshape(self.var.nCrop,self.var.nCell) vars(self.var)[param] = np.broadcast_to( d, (self.var.nFarm, self.var.nCrop, self.var.nCell))
def initial(self): # Define initial water contents self.var.initialConditionFileNC = self.var._configuration.globalOptions[ 'initialConditionNC'] th = vos.netcdf2PCRobjCloneWithoutTime( self.var.initialConditionFileNC, 'th', cloneMapFileName=self.var.cloneMap) init_cond_interp_method = self.var._configuration.globalOptions[ 'InterpMethod'] # init_cond_type = self.var._configuration.globalOptions['initialConditionType'] if init_cond_interp_method.lower() == 'depth': depths = vos.netcdfDim2NumPy(self.var.initialConditionFileNC, 'depth') zBot = np.cumsum(self.var.dz) zTop = zBot - self.var.dz zMid = (zTop + zBot) / 2 # add zero point if depths[0] > 0: depths = np.concatenate([[0.], depths]) th = np.concatenate([th[0, ...][None, :], th], axis=0) if depths[-1] < zBot[-1]: depths = np.concatenate([depths, [zBot[-1]]]) th = np.concatenate([th, th[-1, ...][None, :]], axis=0) # now interpolate to compartments f_thini = interpolate.interp1d(depths, th, axis=0, bounds_error=False, fill_value=(th[0, ...], th[-1, ...])) th = f_thini(zMid) else: th = th[self.var.layerIndex, :, :] # NB original Matlab code also allows users to supply initial condition # as field capacity, wilting point or saturation. We do not explicitly # include this option but of course it is possible to do this by # supplying a netCDF file containing the values. However, note that in # the original version if field capacity is specified and groundwater # table is present the initial water content is set to th_fc_adj once # this variable has been computed. th = np.broadcast_to( th, (self.var.nCrop, self.var.nComp, self.var.nLat, self.var.nLon)) self.var.th = np.copy(th)
def initial_tubewell_capacity(self): # TODO - this is where initial tubewell ownership is read to the model initialTubewellCapacityNC = str( self.configuration['initialTubewellOwnershipInputFile']) tubewell_capacity_varname = str( self.configuration['initialTubewellOwnershipVariableName']) tubewell_count = vos.netcdf2PCRobjCloneWithoutTime( initialTubewellCapacityNC, tubewell_capacity_varname, cloneMapFileName=self.var.cloneMap, LatitudeLongitude=True) mask = np.broadcast_to(self.var.landmask, tubewell_count.shape) tubewell_count = np.reshape(tubewell_count[mask], (self.var.nFarm, self.var.nCell)) self.var.TubewellCount = tubewell_count.copy()
def read_potential_crop_yield(self): if self.var.AnnualChangeInPotYield: if self.var._modelTime.timeStepPCR == 1 or self.var._modelTime.doy == 1: date = '%04i-%02i-%02i' % (self.var._modelTime.year, 1, 1) self.var.Yx = vos.netcdf2PCRobjClone( self.var.PotYieldFileNC, self.var.PotYieldVarName, date, useDoy=None, cloneMapFileName=self.var.cloneMap, LatitudeLongitude=True) else: if self.var._modelTime.timeStepPCR == 1: self.var.Yx = vos.netcdf2PCRobjCloneWithoutTime( self.var.PotYieldFileNC, self.var.PotYieldVarName, cloneMapFileName=self.var.cloneMap)
def initial_water_content(self): landmask = np.broadcast_to( self.var.landmask, (self.var.nLayer, self.var.nLat, self.var.nLon)) self.var.initialConditionFileNC = str( self.var._configuration. INITIAL_CONDITIONS['initialConditionInputFile']) self.var.initialConditionVarName = str( self.var._configuration. INITIAL_CONDITIONS['initialConditionVariableName']) th = vos.netcdf2PCRobjCloneWithoutTime( self.var.initialConditionFileNC, self.var.initialConditionVarName, cloneMapFileName=self.var.cloneMap) th = th[landmask].reshape(self.var.nLayer, self.var.nCell) self.var.th = np.broadcast_to( th[None, None, ...], (self.var.nFarm, self.var.nCrop, self.var.nLayer, self.var.nCell)).copy() self.var.wc = (self.var.th * self.var.root_depth)
def initial(self): initialCanalAccessNC = str( self.configuration['initialCanalAccessInputFile']) canal_access_varname = str( self.configuration['initialCanalAccessVariableName']) try: canal_access = vos.netcdf2PCRobjCloneWithoutTime( initialCanalAccessNC, canal_access_varname, cloneMapFileName=self.var.cloneMap, LatitudeLongitude=True) except: canal_access = np.ones( (self.var.nFarm, self.var.nLat, self.var.nLon)) mask = np.broadcast_to(self.var.landmask, canal_access.shape) canal_access = np.reshape(canal_access[mask], (self.var.nFarm, self.var.nCell)) self.var.CanalAccess = canal_access.copy()
def read_crop_area(self, date = None): if date is None: crop_area = vos.netcdf2PCRobjCloneWithoutTime( self.CropAreaFileNC, self.CropAreaVarName, cloneMapFileName = self.var.cloneMap, LatitudeLongitude = True) else: crop_area = vos.netcdf2PCRobjClone( self.CropAreaFileNC, self.CropAreaVarName, date, useDoy = None, cloneMapFileName = self.var.cloneMap, LatitudeLongitude = True) crop_area = np.reshape( crop_area[self.var.landmask_crop], (self.var.nCrop, self.var.nCell)) crop_area = np.float64(crop_area) return crop_area
def read_potential_crop_yield(self): start_of_model_run = (self.var._modelTime.timeStepPCR == 1) start_of_year = (self.var._modelTime.doy == 1) if self.AnnualChangeInPotYield: if start_of_model_run or start_of_year: date = datetime.datetime(self.var._modelTime.year, 1, 1, 0, 0, 0) Yx = vos.netcdf2PCRobjClone( self.PotYieldNC, self.PotYieldVarName, date, useDoy = None, cloneMapFileName = self.var.cloneMap, LatitudeLongitude = True) self.var.Yx = Yx[self.var.landmask_crop].reshape(self.var.nCrop, self.var.nCell) else: if start_of_model_run: # date = datetime.datetime(self.staticLandCoverYear, 1, 1, 0, 0, 0) # ***TODO*** Yx = vos.netcdf2PCRobjCloneWithoutTime( self.PotYieldNC, self.PotYieldVarName, cloneMapFileName = self.var.cloneMap) self.var.Yx = Yx[self.var.landmask_crop].reshape(self.var.nCrop, self.var.nCell)
def set_farm_category(self): if not self.FarmCategoryFileNC == "None": start_of_model_run = (self.var._modelTime.timeStepPCR == 1) start_of_year = (self.var._modelTime.doy == 1) if self.AnnualChangeInFarmCategory: if start_of_model_run or start_of_year: date = datetime.datetime(self.var._modelTime.year, 1, 1, 0, 0, 0) farm_category_new = vos.netcdf2PCRobjClone( self.FarmCategoryFileNC, self.FarmCategoryVarName, date, useDoy=None, cloneMapFileName=self.var.cloneMap, LatitudeLongitude=True) mask = np.broadcast_to( self.var.landmask, (self.var.nFarm, self.var.nLat, self.var.nLon)) farm_category_new = np.reshape( farm_category_new[mask], (self.var.nFarm, self.var.nCell)) if np.any(self.var.GrowingSeasonDayOne): self.var.FarmCategory[self.var.GrowingSeasonDayOne[ 0, :, :]] = (farm_category_new[ self.var.GrowingSeasonDayOne[0, :, :]]) else: if start_of_model_run: farm_category = vos.netcdf2PCRobjCloneWithoutTime( self.FarmCategoryFileNC, self.FarmCategoryVarName, cloneMapFileName=self.var.cloneMap) mask = np.broadcast_to( self.var.landmask, (self.var.nFarm, self.var.nLat, self.var.nLon)) farm_category = np.reshape( farm_category[mask], (self.var.nFarm, self.var.nCell)) self.var.FarmCategory = farm_category.copy()
def read(self): # method for finding time indexes in the groundwater netdf file: # - the default one method_for_time_index = None # - based on the ini/configuration file (if given) # if 'time_index_method_for_groundwater_netcdf' in self._configuration.GROUNDWATER.keys() and\ # self._configuration.GROUNDWATER['time_index_method_for_groundwater_netcdf'] != "None": # method_for_time_index = self._configuration.GROUNDWATER['time_index_method_for_groundwater_netcdf'] # reading groundwater: if self.WaterTable: if self.VariableWaterTable: # DailyGroundwaterNC is a logical indicating whether a separate # netCDF is used for each time step - use this for coupling if self.DailyGroundwaterNC: # introduce this test so that we do not ask the model to read # a file from a timestep prior to the current simulation. if not (self._modelTime.isFirstTimestep() & (self.gwTimeLag > 0)): tm = self._modelTime.currTime - datetime.timedelta( self.gwTimeLag) day, month, year = tm.day, tm.month, tm.year # Fill named placeholders (NB we have already checked that # the specified filename contains these placeholders) gwFileNC = self.gwFileNC.format(day=day, month=month, year=year) # Check whether the file is present in the filesystem; if # it doesn't, enter a while loop which periodically checks # whether the file exists. We specify a maximum wait time # in order to prevent the model hanging if the file never # materialises. exists = os.path.exists(gwFileNC) max_wait_time = 60 wait_time = 0.1 total_wait_time = 0 while exists is False and total_wait_time <= max_wait_time: time.sleep(wait_time) exists = os.path.exists(gwFileNC) total_wait_time += wait_time if not exists: msg = "groundwater file doesn't exist and maximum wait time exceeded" raise AQError(msg) zGW = vos.netcdf2PCRobjCloneWithoutTime( gwFileNC, self.gwVarName, cloneMapFileName=self.cloneMap, LatitudeLongitude=True) self.zGW = zGW[self.landmask] else: zGW = vos.netcdf2PCRobjClone( self.gwFileNC, self.gwVarName, str(currTimeStep.fulldate), useDoy=method_for_time_index, cloneMapFileName=self.cloneMap, LatitudeLongitude=True) self.zGW = zGW[self.landmask] else: zGW = vos.netcdf2PCRobjCloneWithoutTime( self.gwFileNC, self.gwVarName, cloneMapFileName=self.cloneMap, LatitudeLongitude=True) self.zGW = zGW[self.landmask]
def read(self): # method for finding time indexes in the groundwater netdf file: # - the default one method_for_time_index = None # - based on the ini/configuration file (if given) # if 'time_index_method_for_groundwater_netcdf' in self.var._configuration.groundwaterOptions.keys() and\ # self.var._configuration.groundwaterOptions['time_index_method_for_groundwater_netcdf'] != "None": # method_for_time_index = self.var._configuration.groundwaterOptions['time_index_method_for_groundwater_netcdf'] # reading groundwater: if self.var.WaterTable: if self.var.VariableWaterTable: # DailyForcingData is a logical indicating whether a separate # netCDF is used for each time step - use this for coupling if self.var.DailyForcingData: day, month, year = self.var._modelTime.day, self.var._modelTime.month, self.var._modelTime.year # Fill named placeholders (NB we have already checked that # the specified filename contains these placeholders) gwFileNC = self.var.gwFileNC.format(day=day, month=month, year=year) # Check whether the file is present in the filesystem; if # it doesn't, enter a while loop which periodically checks # whether the file exists. We specify a maximum wait time # in order to prevent the model hanging if the file never # materialises. exists = os.path.exists(gwFileNC) max_wait_time = 60 wait_time = 0.1 total_wait_time = 0 while exists is False and total_wait_time <= max_wait_time: time.sleep(wait_time) exists = os.path.exists(gwFileNC) total_wait_time += wait_time if not exists: print "groundwater file doesn't exist and maximum wait time exceeded" raise # TODO: make error class self.var.zGW = vos.netcdf2PCRobjCloneWithoutTime(gwFileNC, self.var.gwVarName, cloneMapFileName = self.var.cloneMap, LatitudeLongitude = True) else: self.var.zGW = vos.netcdf2PCRobjClone(self.var.gwFileNC, self.var.gwVarName, str(currTimeStep.fulldate), useDoy = method_for_time_index, cloneMapFileName = self.var.cloneMap, LatitudeLongitude = True) else: self.var.zGW = vos.netcdf2PCRobjCloneWithoutTime(self.var.gwFileNC, self.var.gwVarName, cloneMapFileName = self.var.cloneMap, LatitudeLongitude = True) else: self.var.zGW = None
def readSoil(self): # Get layer and compartment thickness (zLayer and dz) from dimensions # Layers: zlayermid = vos.netcdfDim2NumPy(self.var.soilAndTopoFileNC, 'layer') nlayer = zlayermid.size zlayer = np.zeros((nlayer)) runtot = 0 for layer in range(nlayer): zlayer[layer] = (zlayermid[layer] - runtot) * 2 runtot = np.sum(zlayer[:(layer + 1)]) self.var.nLayer = nlayer self.var.zLayer = zlayer # Compartments: zmid = vos.netcdfDim2NumPy(self.var.soilAndTopoFileNC, 'compartment') ncomp = zmid.size dz = np.zeros((ncomp)) runtot = 0 for comp in range(ncomp): dz[comp] = (zmid[comp] - runtot) * 2 runtot = np.sum(dz[:(comp + 1)]) self.var.nComp = ncomp self.var.dz = dz self.var.dzsum = np.cumsum(dz) # These parameters have dimensions depth,lat,lon soilParams1 = ['ksat', 'th_s', 'th_fc', 'th_wp'] for var in soilParams1: d = vos.netcdf2PCRobjCloneWithoutTime( self.var.soilAndTopoFileNC, var, cloneMapFileName=self.var.cloneMap) vars(self.var)[var] = np.broadcast_to( d, (self.var.nCrop, self.var.nLayer, self.var.nLat, self.var.nLon)) # These parameters have dimensions lat,lon soilParams2 = [ 'CalcSHP', 'EvapZsurf', 'EvapZmin', 'EvapZmax', 'Kex', 'fevap', 'fWrelExp', 'fwcc', 'AdjREW', 'REW', 'AdjCN', 'CN', 'zCN', 'zGerm', 'zRes', 'fshape_cr' ] for var in soilParams2: d = vos.netcdf2PCRobjCloneWithoutTime( self.var.soilAndTopoFileNC, var, cloneMapFileName=self.var.cloneMap) d = np.broadcast_to(d, (self.var.nCrop, self.var.nLat, self.var.nLon)) vars(self.var)[var] = np.copy( d ) #np.broadcast_to(d, (self.var.nCrop, self.var.nLat, self.var.nLon)) # map layers to compartments - the result is a 1D array with length # equal to nComp where the value of each element is the index of the # corresponding layer. For the time being we use the layer in which # the midpoint of each compartment is located. # # some data to try the command yourself.var: # # from numpy import np # zMid = np.array((0.05,0.15,0.25,0.375,0.525,0.7,0.9,1.125,1.375,1.625,1.875,2.15)) # zLayerTop = np.array((0,0.5)) # nLayer = 2 zBot = np.cumsum(self.var.dz) zTop = zBot - self.var.dz zMid = (zTop + zBot) / 2 zLayerBot = np.cumsum(self.var.zLayer) zLayerTop = zLayerBot - self.var.zLayer self.var.layerIndex = np.sum(((zMid[:, None] * np.ones( (self.var.nLayer))[None, :]) > zLayerTop), axis=1) - 1 # The following is adapted from AOS_ComputeVariables.m, lines 129-139 # "Calculate drainage characteristic (tau) self.var.tau = 0.0866 * (self.var.ksat**0.35) self.var.tau = np.round(self.var.tau * 100) / 100 self.var.tau[self.var.tau > 1] = 1 self.var.tau[self.var.tau < 0] = 0 # The following is adapted from AOS_ComputeVariables.m, lines 25 self.var.th_dry = self.var.th_wp / 2 cond = (self.var.AdjREW == 0) self.var.REW[cond] = (np.round( (1000 * (self.var.th_fc[:, 0, ...] - self.var.th_dry[:, 0, ...]) * self.var.EvapZsurf)))[cond] # The following is adapted from AOS_ComputeVariables.m, lines 147-151 # "Calculate upper and lower curve numbers" self.var.CNbot = np.round(1.4 * (np.exp(-14 * np.log(10))) + (0.507 * self.var.CN) - (0.00374 * self.var.CN**2) + (0.0000867 * self.var.CN**3)) self.var.CNtop = np.round(5.6 * (np.exp(-14 * np.log(10))) + (2.33 * self.var.CN) - (0.0209 * self.var.CN**2) + (0.000076 * self.var.CN**3)) # transform certain soil properties to (ncrop, ncomp, nlat, nlon) soil_params = ['th_s', 'th_fc', 'th_wp', 'th_dry', 'ksat', 'tau'] # soil_params = ['th_s','th_fc','th_wp','th_dry','ksat','tau','fshape_cr'] for nm in soil_params: newnm = nm + '_comp' vars(self.var)[newnm] = vars(self.var)[nm][:, self.var.layerIndex, ...]
def read(self): self.var.nLayer = 3 # soil depths soildepth0 = np.full((self.var.nLat, self.var.nLon), 0.05)[self.var.landmask] soildepth1 = vos.netcdf2PCRobjCloneWithoutTime( str(self.var._configuration.SOIL['soilDepthOneInputFile']), str(self.var._configuration.SOIL['soilDepthOneVariableName']), cloneMapFileName=self.var.cloneMap)[self.var.landmask] soildepth1 = np.maximum(0.05, soildepth1 - soildepth0) soildepth2 = vos.netcdf2PCRobjCloneWithoutTime( str(self.var._configuration.SOIL['soilDepthTwoInputFile']), str(self.var._configuration.SOIL['soilDepthTwoVariableName']), cloneMapFileName=self.var.cloneMap)[self.var.landmask] soildepth2 = np.maximum(0.05, soildepth2) soil_depth = np.stack([soildepth0, soildepth1, soildepth2]) # CALIBRATION self.var.soildepth_factor = 1. # TODO: read from configuration soil_depth[1] *= self.var.soildepth_factor soil_depth[2] *= self.var.soildepth_factor self.var.soil_depth = np.broadcast_to( soil_depth[None, None, :, :], (self.var.nFarm, self.var.nCrop, self.var.nLayer, self.var.nCell)) # crop group number # TODO: would it make more sense to have this per crop? self.var.crop_group_number = vos.netcdf2PCRobjCloneWithoutTime( str(self.var._configuration.SOIL['cropGroupNumberInputFile']), str(self.var._configuration.SOIL['cropGroupNumberVariableName']), cloneMapFileName=self.var.cloneMap)[self.var.landmask] # These parameters have dimensions depth,lat,lon landmask = np.broadcast_to( self.var.landmask, (self.var.nLayer, self.var.nLat, self.var.nLon)) ksat = vos.netcdf2PCRobjCloneWithoutTime( str(self.lc_configuration['KsatInputFile']), str(self.lc_configuration['KsatVariableName']), cloneMapFileName=self.var.cloneMap) ksat = ksat[landmask].reshape(self.var.nLayer, self.var.nCell) self.var.ksat = np.broadcast_to( ksat[None, None, :, :], (self.var.nFarm, self.var.nCrop, self.var.nLayer, self.var.nCell)).copy() self.var.ksat /= 100. # cm d-1 -> m d-1 ***TODO*** put factor in config # Saturated water content th_s = vos.netcdf2PCRobjCloneWithoutTime( self.lc_configuration['saturatedWaterContentInputFile'], self.lc_configuration['saturatedWaterContentVariableName'], cloneMapFileName=self.var.cloneMap) th_s = th_s[landmask].reshape(self.var.nLayer, self.var.nCell) self.var.th_s = np.broadcast_to( th_s[None, None, :, :], (self.var.nFarm, self.var.nCrop, self.var.nLayer, self.var.nCell)) # # Field capacity # th_fc = vos.netcdf2PCRobjCloneWithoutTime( # self.lc_configuration['fieldCapacityInputFile'], # self.lc_configuration['fieldCapacityVariableName'], # cloneMapFileName=self.var.cloneMap) # th_fc = th_fc[landmask].reshape(self.var.nLayer,self.var.nCell) # self.var.th_fc = np.broadcast_to(th_fc[None,None,:,:], (self.var.nFarm, self.var.nCrop, self.var.nLayer, self.var.nCell)) # # Wilting point # th_wp = vos.netcdf2PCRobjCloneWithoutTime( # self.lc_configuration['wiltingPointInputFile'], # self.lc_configuration['wiltingPointVariableName'], # cloneMapFileName=self.var.cloneMap) # th_wp = th_wp[landmask].reshape(self.var.nLayer,self.var.nCell) # self.var.th_wp = np.broadcast_to(th_wp[None,None,:,:], (self.var.nFarm, self.var.nCrop, self.var.nLayer, self.var.nCell)) # Residual water content th_res = vos.netcdf2PCRobjCloneWithoutTime( self.lc_configuration['residualWaterContentInputFile'], self.lc_configuration['residualWaterContentVariableName'], cloneMapFileName=self.var.cloneMap) th_res = th_res[landmask].reshape(self.var.nLayer, self.var.nCell) self.var.th_res = np.broadcast_to( th_res[None, None, :, :], (self.var.nFarm, self.var.nCrop, self.var.nLayer, self.var.nCell)) # # The following is adapted from AOS_ComputeVariables.m, lines 25 # self.var.th_dry = self.var.th_wp / 2 # Van Genuchten alpha shape parameter van_genuchten_alpha = vos.netcdf2PCRobjCloneWithoutTime( self.lc_configuration['alphaInputFile'], self.lc_configuration['alphaVariableName'], cloneMapFileName=self.var.cloneMap) van_genuchten_alpha = van_genuchten_alpha[landmask].reshape( self.var.nLayer, self.var.nCell) self.var.van_genuchten_alpha = np.broadcast_to( van_genuchten_alpha[None, None, :, :], (self.var.nFarm, self.var.nCrop, self.var.nLayer, self.var.nCell)) # Van Genuchten lambda shape parameter van_genuchten_lambda = vos.netcdf2PCRobjCloneWithoutTime( self.lc_configuration['lambdaInputFile'], self.lc_configuration['lambdaVariableName'], cloneMapFileName=self.var.cloneMap) van_genuchten_lambda = van_genuchten_lambda[landmask].reshape( self.var.nLayer, self.var.nCell) self.var.van_genuchten_lambda = np.broadcast_to( van_genuchten_lambda[None, None, :, :], (self.var.nFarm, self.var.nCrop, self.var.nLayer, self.var.nCell))
def set_grid_cell_area(self): grid_cell_area = vos.netcdf2PCRobjCloneWithoutTime( str(self._configuration.MASK_OUTLET['gridCellAreaInputFile']), str(self._configuration.MASK_OUTLET['gridCellAreaVariableName']), cloneMapFileName = self.cloneMap) self.grid_cell_area = grid_cell_area[self.landmask]