12 use missing_values_mod
14 use oops_variables_mod
30 integer,
allocatable :: qcflags(:,:)
31 real(kind_real),
allocatable :: yobs(:,:)
32 real(kind_real),
allocatable :: ybias(:,:)
33 real(kind_real),
allocatable :: lat(:)
34 real(kind_real),
allocatable :: lon(:)
35 real(kind_real),
allocatable :: elevation(:)
36 real(kind_real),
allocatable :: sat_zen(:)
37 real(kind_real),
allocatable :: sat_azi(:)
38 real(kind_real),
allocatable :: sol_zen(:)
39 real(kind_real),
allocatable :: sol_azi(:)
40 integer,
allocatable :: surface_type(:)
41 integer,
allocatable :: niter(:)
42 real(kind_real),
allocatable :: final_cost(:)
43 real(kind_real),
allocatable :: lwp(:)
44 real(kind_real),
allocatable :: emiss(:,:)
45 real(kind_real),
allocatable :: output_profile(:,:)
46 real(kind_real),
allocatable :: output_bt(:,:)
47 real(kind_real),
allocatable :: background_bt(:,:)
48 logical,
allocatable :: calc_emiss(:)
49 logical :: store1dvarlwp
79 integer,
intent(in) :: nprofelements
81 type(oops_variables),
intent(in) :: vars
84 character(len=*),
parameter :: routinename =
"ufo_rttovonedvarcheck_obs_init"
85 real(kind_real) :: missing
88 character(len=max_string) :: var
89 character(len=max_string) :: varname
90 logical :: variable_present = .false.
91 logical :: model_surface_present = .false.
94 missing = missing_value(missing)
95 self % iloc = obsspace_get_nlocs(config % obsdb)
98 allocate(self % yobs(config % nchans, self % iloc))
99 allocate(self % ybias(config % nchans, self % iloc))
100 allocate(self % QCflags(config % nchans, self % iloc))
101 allocate(self % lat(self % iloc))
102 allocate(self % lon(self % iloc))
103 allocate(self % elevation(self % iloc))
104 allocate(self % sat_zen(self % iloc))
105 allocate(self % sat_azi(self % iloc))
106 allocate(self % sol_zen(self % iloc))
107 allocate(self % sol_azi(self % iloc))
108 allocate(self % surface_type(self % iloc))
109 allocate(self % niter(self % iloc))
110 allocate(self % final_cost(self % iloc))
111 allocate(self % LWP(self % iloc))
112 allocate(self % emiss(config % nchans, self % iloc))
113 allocate(self % output_profile(nprofelements, self % iloc))
114 allocate(self % output_BT(config % nchans, self % iloc))
115 allocate(self % background_BT(config % nchans, self % iloc))
116 allocate(self % calc_emiss(self % iloc))
119 self % yobs(:,:) = missing
120 self % ybias(:,:) =
zero
121 self % QCflags(:,:) = 0
122 self % lat(:) = missing
123 self % lon(:) = missing
124 self % elevation(:) = missing
125 self % sat_zen(:) = missing
126 self % sat_azi(:) =
zero
127 self % sol_zen(:) =
zero
128 self % sol_azi(:) =
zero
129 self % surface_type(:) =
rtsea
131 self % final_cost(:) = missing
132 self % LWP(:) = missing
133 self % emiss(:,:) =
zero
134 self % output_profile(:,:) = missing
135 self % output_BT(:,:) = missing
136 self % background_BT(:,:) = missing
137 self % calc_emiss(:) = .true.
138 self % Store1DVarLWP = config % Store1DVarLWP
141 do jvar = 1, config % nchans
143 var = vars % variable(jvar)
144 call obsspace_get_db(config % obsdb,
"FortranQC", trim(var), self % QCflags(jvar,:))
145 call obsspace_get_db(config % obsdb,
"ObsValue", trim(var), self % yobs(jvar,:))
148 variable_present = obsspace_has(config % obsdb,
"ObsBias", trim(var))
149 if (variable_present)
then
150 call obsspace_get_db(config % obsdb,
"ObsBias", trim(var), self % ybias(jvar,:))
158 do jobs = 1, self % iloc
159 do jvar = 1, config % nchans
160 if (self % ybias(jvar, jobs) == missing)
then
161 self % ybias(jvar, jobs) =
zero
166 if (.not. variable_present)
write(*,*)
"Using uncorrected brightness temperature"
169 self % yobs = self % yobs - self % ybias
172 call obsspace_get_db(config % obsdb,
"MetaData",
"latitude", self % lat(:))
173 call obsspace_get_db(config % obsdb,
"MetaData",
"longitude", self % lon(:))
174 call obsspace_get_db(config % obsdb,
"MetaData",
"sensor_zenith_angle", self % sat_zen(:))
177 variable_present = obsspace_has(config % obsdb,
"MetaData",
"sensor_azimuth_angle")
178 if (variable_present)
then
179 call obsspace_get_db(config % obsdb,
"MetaData",
"sensor_azimuth_angle", self % sat_azi(:))
182 variable_present = obsspace_has(config % obsdb,
"MetaData",
"solar_zenith_angle")
183 if (variable_present)
then
184 call obsspace_get_db(config % obsdb,
"MetaData",
"solar_zenith_angle", self % sol_zen(:))
187 variable_present = obsspace_has(config % obsdb,
"MetaData",
"solar_azimuth_angle")
188 if (variable_present)
then
189 call obsspace_get_db(config % obsdb,
"MetaData",
"solar_azimuth_angle", self % sol_azi(:))
193 if (obsspace_has(config % obsdb,
"MetaData",
"elevation"))
then
194 call obsspace_get_db(config % obsdb,
"MetaData",
"elevation", self % elevation(:))
195 else if (obsspace_has(config % obsdb,
"MetaData",
"surface_height"))
then
196 call obsspace_get_db(config % obsdb,
"MetaData",
"surface_height", self % elevation(:))
197 else if (obsspace_has(config % obsdb,
"MetaData",
"model_orography"))
then
198 call obsspace_get_db(config % obsdb,
"MetaData",
"model_orography", self % elevation(:))
201 self % elevation(:) = geoval%vals(1, 1)
203 self % elevation(:) =
zero
207 if (obsspace_has(config % obsdb,
"MetaData",
"surface_type"))
then
208 call obsspace_get_db(config % obsdb,
"MetaData",
"surface_type", self % surface_type(:))
211 self % surface_type(:) = geoval%vals(1, :)
215 if (config % pcemiss)
then
216 write(*,*)
"PC emissivity being used"
219 write(*,*)
"Conventional emissivity being used"
239 character(len=*),
parameter :: routinename =
"ufo_rttovonedvarcheck_obs_delete"
242 if (
allocated(self % QCflags))
deallocate(self % QCflags)
243 if (
allocated(self % yobs))
deallocate(self % yobs)
244 if (
allocated(self % ybias))
deallocate(self % ybias)
245 if (
allocated(self % lat))
deallocate(self % lat)
246 if (
allocated(self % lon))
deallocate(self % lon)
247 if (
allocated(self % elevation))
deallocate(self % elevation)
248 if (
allocated(self % sat_zen))
deallocate(self % sat_zen)
249 if (
allocated(self % sat_azi))
deallocate(self % sat_azi)
250 if (
allocated(self % sol_zen))
deallocate(self % sol_zen)
251 if (
allocated(self % sol_azi))
deallocate(self % sol_azi)
252 if (
allocated(self % surface_type))
deallocate(self % surface_type)
253 if (
allocated(self % niter))
deallocate(self % niter)
254 if (
allocated(self % final_cost))
deallocate(self % final_cost)
255 if (
allocated(self % LWP))
deallocate(self % LWP)
256 if (
allocated(self % emiss))
deallocate(self % emiss)
257 if (
allocated(self % output_profile))
deallocate(self % output_profile)
258 if (
allocated(self % output_BT))
deallocate(self % output_BT)
259 if (
allocated(self % background_BT))
deallocate(self % background_BT)
260 if (
allocated(self % calc_emiss))
deallocate(self % calc_emiss)
287 do i = 1, self % iloc
290 if (self % surface_type(i) ==
rtsea)
then
291 self % calc_emiss(i) = .true.
293 self % calc_emiss(i) = .false.
299 self % emiss(:,i) =
zero
300 if (self % surface_type(i) ==
rtland)
then
301 self % emiss(:,i) = config % EmissLandDefault
302 else if (self % surface_type(i) ==
rtice)
then
303 self % emiss(:,i) = config % EmissSeaIceDefault
325 integer,
intent(in) :: nchans
329 real(kind_real),
allocatable :: EmissPC(:,:)
331 integer :: nemisspc = 5
336 self % emiss(:,:) =
zero
337 self % calc_emiss(:) = .true.
339 allocate(emisspc(self % iloc,nemisspc))
346 if (ir_pcemis % initialised)
then
351 if (
associated (ir_pcemis % emis_eigen % PCGuess))
then
353 do i = 1, self % iloc
359 if (
associated (ir_pcemis % emis_atlas % EmisPC))
then
362 emis_y = nint((self % lat(i) + 90.0_kind_real) / &
363 ir_pcemis % emis_atlas % gridstep + 1)
364 emis_x = nint((self % lon(i) + 180.0_kind_real) / &
365 ir_pcemis % emis_atlas % gridstep + 1)
366 if (emis_x > ir_pcemis % emis_atlas % nlon)
then
367 emis_x = emis_x - ir_pcemis % emis_atlas % nlon
373 if (any(ir_pcemis % emis_atlas % EmisPC(emis_x,emis_y,:) > -9.99_kind_real))
then
374 emisspc(i,:) = ir_pcemis % emis_atlas % EmisPC(emis_x,emis_y,1:nemisspc)
376 emisspc(i,:) = ir_pcemis % emis_eigen % PCGuess(1:nemisspc)
384 emisspc(i,:) = ir_pcemis % emis_eigen % PCGuess(1:nemisspc)
393 if (
allocated(emisspc))
deallocate(emisspc)
412 type(c_ptr),
value,
intent(in) :: obsdb
414 type(oops_variables),
intent(in) :: vars
415 integer,
intent(in) :: nchans
420 character(len=max_string) :: var
421 real(kind_real),
allocatable :: surface_pressure(:)
422 real(kind_real) :: missing
424 missing = missing_value(missing)
428 var = vars % variable(jvar)
429 call obsspace_put_db(obsdb,
"FortranQC", trim(var), self % QCflags(jvar,:))
430 call obsspace_put_db(obsdb,
"OneDVar", trim(var), self % output_BT(jvar,:))
431 call obsspace_put_db(obsdb,
"OneDVarBack", trim(var), self % background_BT(jvar,:))
435 call obsspace_put_db(obsdb,
"OneDVar",
"FinalCost", self % final_cost(:))
436 nobs =
size(self % final_cost(:))
437 call obsspace_put_db(obsdb,
"OneDVar",
"n_iterations", self % niter(:))
439 if (self % Store1DVarLWP)
then
440 call obsspace_put_db(obsdb,
"OneDVar",
"LWP", self % LWP(:))
455 if (prof_index % pstar > 0)
THEN
456 allocate(surface_pressure(nobs))
457 surface_pressure(:) = self % output_profile(prof_index % pstar, :)
458 where (surface_pressure /= missing)
459 surface_pressure = surface_pressure /
pa_to_hpa
461 call obsspace_put_db(obsdb,
"OneDVar", trim(
var_ps), surface_pressure)
462 deallocate(surface_pressure)
468 if (prof_index % t2 > 0)
THEN
469 call obsspace_put_db(obsdb,
"OneDVar", trim(
var_sfc_t2m), &
470 self % output_profile(prof_index % t2, :))
482 if (prof_index % windspeed > 0)
then
483 call obsspace_put_db(obsdb,
"OneDVar",
"surface_wind_speed", &
484 self % output_profile(prof_index % windspeed, :))
490 if (prof_index % tstar > 0)
then
491 call obsspace_put_db(obsdb,
"OneDVar", trim(
var_sfc_tskin), &
492 self % output_profile(prof_index % tstar, :))
real(kind_real), parameter, public zero
real(kind_real), parameter, public pa_to_hpa
subroutine, public ufo_geovals_get_var(self, varname, geoval)
Fortran module constants used throughout the rttovonedvarcheck filter.
integer, parameter, public rtsea
integer for sea surface type
integer, parameter, public rtland
integer for land surface type
integer, parameter, public rtice
integer for seaice surface type
Fortran module which contains the observation data for a all the obs space.
subroutine ufo_rttovonedvarcheck_obs_delete(self)
Delete the observation object.
subroutine ufo_rttovonedvarcheck_obs_setup(self, config, nprofelements, geovals, vars, ir_pcemis)
Initialize observation object.
subroutine ufo_rttovonedvarcheck_obs_output(self, obsdb, prof_index, vars, nchans)
Store the 1D-Var analysis variables in obsspace for future assessment.
subroutine ufo_rttovonedvarcheck_obs_initiremiss(self, nchans, ir_pcemis)
Initialize the infrared emissivity array.
subroutine ufo_rttovonedvarcheck_obs_initmwemiss(self, config)
Initialize the microwave emissivity array.
Fortran module which contains the methods for Infrared Principal Component Emissivity The science can...
Fortran module containing profile index.
Fortran module containing main type, setup and utilities for the main rttovonedvarcheck object.
integer function, public ufo_vars_getindex(vars, varname)
character(len=maxvarlen), parameter, public var_sfc_tskin
character(len=maxvarlen), parameter, public var_ps
character(len=maxvarlen), parameter, public var_sfc_t2m
type to hold interpolated field for one variable, one observation
type to hold interpolated fields required by the obs operators