Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
DART-WRF
Manage
Activity
Members
Labels
Plan
Issues
Issue boards
Milestones
Wiki
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Snippets
Deploy
Releases
Package registry
Model registry
Operate
Terraform modules
Monitor
Incidents
Service Desk
Analyze
Value stream analytics
Contributor analytics
Repository analytics
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
GitLab community forum
Contribute to GitLab
Provide feedback
Terms and privacy
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
DataAssimilation
DART-WRF
Commits
e94e9a8a
Commit
e94e9a8a
authored
Oct 17, 2020
by
Lukas Kugler
Browse files
Options
Downloads
Patches
Plain Diff
restructure obs_loc
parent
b1a3f873
Branches
Branches containing commit
Tags
Tags containing commit
No related merge requests found
Changes
3
Show whitespace changes
Inline
Side-by-side
Showing
3 changed files
config/cfg.py
+6
-3
6 additions, 3 deletions
config/cfg.py
scripts/create_obsseq.py
+17
-30
17 additions, 30 deletions
scripts/create_obsseq.py
scripts/gen_synth_obs.py
+27
-24
27 additions, 24 deletions
scripts/gen_synth_obs.py
with
50 additions
and
57 deletions
config/cfg.py
+
6
−
3
View file @
e94e9a8a
...
@@ -12,12 +12,15 @@ exp.model_dx = 2000
...
@@ -12,12 +12,15 @@ exp.model_dx = 2000
exp
.
timestep
=
10
exp
.
timestep
=
10
exp
.
n_ens
=
40
exp
.
n_ens
=
40
exp
.
n_nodes
=
10
exp
.
n_nodes
=
10
exp
.
n_obs
=
81
# radar: n_obs for each observation height level
n_obs
=
81
# radar: n_obs for each observation height level
vis
=
dict
(
sat
=
True
,
channel
=
1
,
n_obs
=
n_obs
,
err_std
=
0.03
,
vis
=
dict
(
sat
=
True
,
channel
=
1
,
n_obs
=
n_obs
,
err_std
=
0.03
,
distance_between_obs_meters
=
50000
,)
distance_between_obs_km
=
50
,
cov_loc_radius_km
=
10
)
radar
=
dict
(
sat
=
False
,
kind
=
'
radar
'
,
n_obs
=
n_obs
,
err_std
=
5.
,
radar
=
dict
(
sat
=
False
,
kind
=
'
radar
'
,
n_obs
=
n_obs
,
err_std
=
5.
,
distance_between_obs_meters
=
50000
,)
distance_between_obs_km
=
50
,
cov_loc_radius_km
=
10
)
exp
.
observations
=
[
vis
,]
exp
.
observations
=
[
vis
,]
...
...
This diff is collapsed.
Click to expand it.
scripts/create_obsseq.py
+
17
−
30
View file @
e94e9a8a
...
@@ -33,13 +33,18 @@ def get_dart_date(time_dt):
...
@@ -33,13 +33,18 @@ def get_dart_date(time_dt):
secs_thatday
=
str
(
int
((
time_dt
-
round_to_day
(
time_dt
)).
total_seconds
()))
secs_thatday
=
str
(
int
((
time_dt
-
round_to_day
(
time_dt
)).
total_seconds
()))
return
dart_date_day
,
secs_thatday
return
dart_date_day
,
secs_thatday
def
calc_obs_locations
(
n_obs
,
distance_between_obs_meters
,
def
calc_obs_locations
(
n_obs
,
coords_from_domaincenter
=
True
,
coords_from_domaincenter
=
True
,
fpath_obs_locations
=
False
):
distance_between_obs_km
=
9999
,
fpath_obs_locations
=
False
):
"""
Calculate coordinate pairs for locations
"""
Calculate coordinate pairs for locations
Args:
Args:
n_obs (int):
n_obs (int):
number of observations (must be a square of an integer: 4, 9, 1000, ...)
number of observations (must be a square of an integer: 4, 9, 1000, ...)
coords_from_domaincenter (bool):
if False: spread observations evenly
if True: spread from domaincenter, `distance_between_obs_km` apart
distance_between_obs_km (int):
only used when coords_from_domaincenter=True
fpath_obs_locations (False or str):
fpath_obs_locations (False or str):
write an obs_coords.pkl, can be used to check observation locations
write an obs_coords.pkl, can be used to check observation locations
if str, write to file
if str, write to file
...
@@ -60,6 +65,7 @@ def calc_obs_locations(n_obs, distance_between_obs_meters,
...
@@ -60,6 +65,7 @@ def calc_obs_locations(n_obs, distance_between_obs_meters,
nx
,
ny
=
int
(
np
.
sqrt
(
n_obs
)),
int
(
np
.
sqrt
(
n_obs
))
nx
,
ny
=
int
(
np
.
sqrt
(
n_obs
)),
int
(
np
.
sqrt
(
n_obs
))
m_per_degree
=
2
*
np
.
pi
*
radius_earth_meters
/
360
m_per_degree
=
2
*
np
.
pi
*
radius_earth_meters
/
360
distance_between_obs_meters
=
distance_between_obs_km
*
1000.
dy_4km_in_degree
=
distance_between_obs_meters
/
m_per_degree
dy_4km_in_degree
=
distance_between_obs_meters
/
m_per_degree
for
iy
in
range
(
int
(
-
ny
/
2
),
int
(
ny
/
2
+
1
)):
for
iy
in
range
(
int
(
-
ny
/
2
),
int
(
ny
/
2
+
1
)):
...
@@ -157,27 +163,22 @@ kind
...
@@ -157,27 +163,22 @@ kind
f
.
write
(
msg
)
f
.
write
(
msg
)
print
(
fpath
,
'
saved.
'
)
print
(
fpath
,
'
saved.
'
)
def
sat
(
time_dt
,
channel_id
,
n_obs
,
error_var
,
distance_between_obs_meters
,
def
sat
(
time_dt
,
channel_id
,
coords
,
error_var
,
output_path
=
'
./
'
):
output_path
=
'
./
'
,
fpath_obs_locations
=
False
):
"""
Create obs_seq.in
"""
Create obs_seq.in
Args:
Args:
time_dt (dt.datetime): time of observation
time_dt (dt.datetime): time of observation
channel_id (int): SEVIRI channel number
channel_id (int): SEVIRI channel number
see https://nwp-saf.eumetsat.int/downloads/rtcoef_rttov12/ir_srf/rtcoef_msg_4_seviri_srf.html
see https://nwp-saf.eumetsat.int/downloads/rtcoef_rttov12/ir_srf/rtcoef_msg_4_seviri_srf.html
n_obs (int):
coords (list of 2-tuples with (lat,lon))
number of observations squared (must be a square of an integer: 4, 9, 1000, ...)
error_var (float):
error_var (float):
gaussian error with this variance is added to the truth at observation time
gaussian error with this variance is added to the truth at observation time
output_path (str): directory where `obs_seq.in` will be saved
output_path (str): directory where `obs_seq.in` will be saved
fpath_obs_locations (False or str):
write an obs_coords.pkl, can be used to check observation locations
if str, write to file
"""
"""
# time_dt = add_timezone_UTC(time_dt)
# time_dt = add_timezone_UTC(time_dt)
# time_dt = dt.datetime(2008, 7, 30, 15, 30, tzinfo=dt.timezone.utc)
# time_dt = dt.datetime(2008, 7, 30, 15, 30, tzinfo=dt.timezone.utc)
assert
n_obs
==
int
(
n_obs
)
error_var
=
str
(
error_var
)
error_var
=
str
(
error_var
)
n_obs
=
len
(
coords
)
# Brightness temperature or Reflectance?
# Brightness temperature or Reflectance?
channel_id
=
int
(
channel_id
)
channel_id
=
int
(
channel_id
)
...
@@ -189,10 +190,6 @@ def sat(time_dt, channel_id, n_obs, error_var, distance_between_obs_meters,
...
@@ -189,10 +190,6 @@ def sat(time_dt, channel_id, n_obs, error_var, distance_between_obs_meters,
code
=
'
255
'
code
=
'
255
'
channel_id
=
str
(
channel_id
)
channel_id
=
str
(
channel_id
)
coords
=
calc_obs_locations
(
n_obs
,
distance_between_obs_meters
,
coords_from_domaincenter
=
False
,
fpath_obs_locations
=
fpath_obs_locations
)
time_dt
=
add_timezone_UTC
(
time_dt
)
time_dt
=
add_timezone_UTC
(
time_dt
)
sun_az
=
str
(
get_azimuth
(
lat0
,
lon0
,
time_dt
))
sun_az
=
str
(
get_azimuth
(
lat0
,
lon0
,
time_dt
))
sun_zen
=
str
(
90.
-
get_altitude
(
lat0
,
lon0
,
time_dt
))
sun_zen
=
str
(
90.
-
get_altitude
(
lat0
,
lon0
,
time_dt
))
...
@@ -269,13 +266,7 @@ kind
...
@@ -269,13 +266,7 @@ kind
print
(
fpath
,
'
saved.
'
)
print
(
fpath
,
'
saved.
'
)
def
gen_coords
(
n_obs
,
distance_between_obs_meters
,
heights
,
def
calc_obs_locations_3d
(
coords
,
heights
):
coords_from_domaincenter
=
True
,
fpath_obs_locations
=
False
):
coords
=
calc_obs_locations
(
n_obs
,
distance_between_obs_meters
,
coords_from_domaincenter
=
coords_from_domaincenter
,
fpath_obs_locations
=
fpath_obs_locations
)
# append height
# append height
coords2
=
[]
coords2
=
[]
for
i
in
range
(
len
(
coords
)):
for
i
in
range
(
len
(
coords
)):
...
@@ -288,18 +279,14 @@ def gen_coords(n_obs, distance_between_obs_meters, heights,
...
@@ -288,18 +279,14 @@ def gen_coords(n_obs, distance_between_obs_meters, heights,
return
coords2
return
coords2
def
generic_obs
(
obs_type
,
time_dt
,
n_obs
,
error_var
,
distance_between_obs_meters
,
def
generic_obs
(
obs_type
,
time_dt
,
coords
,
error_var
,
output_path
=
'
./
'
):
output_path
=
'
./
'
,
fpath_obs_locations
=
False
):
obs_codes
=
{
'
RASO_T
'
:
{
'
name
'
:
'
RADIOSONDE_TEMPERATURE
'
,
'
nr
'
:
'
5
'
},
obs_codes
=
{
'
RASO_T
'
:
{
'
name
'
:
'
RADIOSONDE_TEMPERATURE
'
,
'
nr
'
:
'
5
'
},
'
RADAR
'
:
{
'
name
'
:
'
RADAR_REFLECTIVITY
'
,
'
nr
'
:
'
37
'
}
'
RADAR
'
:
{
'
name
'
:
'
RADAR_REFLECTIVITY
'
,
'
nr
'
:
'
37
'
}
}
}
heights
=
np
.
arange
(
1000
,
15001
,
1000
)
heights
=
np
.
arange
(
1000
,
15001
,
1000
)
coords
=
calc_obs_locations_3d
(
coords
,
heights
)
coords
=
gen_coords
(
n_obs
,
distance_between_obs_meters
,
heights
,
coords_from_domaincenter
=
False
,
fpath_obs_locations
=
fpath_obs_locations
)
dart_date_day
,
secs_thatday
=
get_dart_date
(
time_dt
)
dart_date_day
,
secs_thatday
=
get_dart_date
(
time_dt
)
print
(
'
secs, days:
'
,
secs_thatday
,
dart_date_day
)
print
(
'
secs, days:
'
,
secs_thatday
,
dart_date_day
)
...
...
This diff is collapsed.
Click to expand it.
scripts/gen_synth_obs.py
+
27
−
24
View file @
e94e9a8a
...
@@ -4,7 +4,9 @@ import numpy as np
...
@@ -4,7 +4,9 @@ import numpy as np
from
scipy.interpolate
import
interp1d
from
scipy.interpolate
import
interp1d
from
config.cfg
import
exp
,
cluster
from
config.cfg
import
exp
,
cluster
from
utils
import
symlink
,
copy
,
sed_inplace
,
append_file
from
utils
import
symlink
,
copy
,
sed_inplace
,
append_file
import
create_obsseq
import
create_obsseq
as
osq
earth_radius_km
=
6370
# fit of Fig 7, Harnisch 2016
# fit of Fig 7, Harnisch 2016
x_ci
=
[
0
,
5
,
10.5
,
13
,
16
]
x_ci
=
[
0
,
5
,
10.5
,
13
,
16
]
...
@@ -70,7 +72,8 @@ def edit_obserr_in_obsseq(fpath_obsseqin, OEs):
...
@@ -70,7 +72,8 @@ def edit_obserr_in_obsseq(fpath_obsseqin, OEs):
for
line
in
obsseq_new
:
for
line
in
obsseq_new
:
f
.
write
(
line
)
f
.
write
(
line
)
def
set_input_nml
(
sat_channel
=
False
,
just_prior_values
=
False
):
def
set_input_nml
(
sat_channel
=
False
,
just_prior_values
=
False
,
cov_loc_radius_km
=
32
):
"""
descr
"""
"""
descr
"""
if
just_prior_values
:
if
just_prior_values
:
template
=
cluster
.
scriptsdir
+
'
/../templates/input.prioronly.nml
'
template
=
cluster
.
scriptsdir
+
'
/../templates/input.prioronly.nml
'
...
@@ -78,6 +81,8 @@ def set_input_nml(sat_channel=False, just_prior_values=False):
...
@@ -78,6 +81,8 @@ def set_input_nml(sat_channel=False, just_prior_values=False):
template
=
cluster
.
scriptsdir
+
'
/../templates/input.nml
'
template
=
cluster
.
scriptsdir
+
'
/../templates/input.nml
'
copy
(
template
,
cluster
.
dartrundir
+
'
/input.nml
'
)
copy
(
template
,
cluster
.
dartrundir
+
'
/input.nml
'
)
sed_inplace
(
cluster
.
dartrundir
+
'
/input.nml
'
,
'
<n_ens>
'
,
str
(
int
(
exp
.
n_ens
)))
sed_inplace
(
cluster
.
dartrundir
+
'
/input.nml
'
,
'
<n_ens>
'
,
str
(
int
(
exp
.
n_ens
)))
cov_loc_radian
=
cov_loc_radius_km
/
earth_radius_km
sed_inplace
(
cluster
.
dartrundir
+
'
/input.nml
'
,
'
<cov_loc_radian>
'
,
str
(
cov_loc_radian
))
# input.nml for RTTOV
# input.nml for RTTOV
if
sat_channel
>
0
:
if
sat_channel
>
0
:
...
@@ -91,6 +96,7 @@ def set_input_nml(sat_channel=False, just_prior_values=False):
...
@@ -91,6 +96,7 @@ def set_input_nml(sat_channel=False, just_prior_values=False):
if
__name__
==
"
__main__
"
:
if
__name__
==
"
__main__
"
:
time
=
dt
.
datetime
.
strptime
(
sys
.
argv
[
1
],
'
%Y-%m-%d_%H:%M
'
)
time
=
dt
.
datetime
.
strptime
(
sys
.
argv
[
1
],
'
%Y-%m-%d_%H:%M
'
)
fpath_obs_coords
=
cluster
.
archivedir
()
+
time
.
strftime
(
'
/%Y-%m-%d_%H:%M/obs_coords.pkl
'
)
# remove any existing observation files
# remove any existing observation files
os
.
system
(
'
rm -f
'
+
cluster
.
dartrundir
+
'
/obs_seq_*.out
'
)
os
.
system
(
'
rm -f
'
+
cluster
.
dartrundir
+
'
/obs_seq_*.out
'
)
...
@@ -100,32 +106,27 @@ if __name__ == "__main__":
...
@@ -100,32 +106,27 @@ if __name__ == "__main__":
n_obs
=
obscfg
[
'
n_obs
'
]
n_obs
=
obscfg
[
'
n_obs
'
]
error_var
=
(
obscfg
[
'
err_std
'
])
**
2
error_var
=
(
obscfg
[
'
err_std
'
])
**
2
distance_between_obs_meters
=
obscfg
[
'
distance_between_obs_meters
'
]
sat_channel
=
obscfg
.
get
(
'
channel
'
,
False
)
cov_loc
=
obscfg
.
get
[
'
cov_loc_radius_km
'
]
dist_obs
=
obscfg
.
get
(
'
distance_between_obs_km
'
,
False
)
# generate obs_seq.in
# generate obs_seq.in
if
not
obscfg
[
'
sat
'
]:
obs_coords
=
osq
.
calc_obs_locations
(
n_obs
,
coords_from_domaincenter
=
False
,
create_obsseq
.
generic_obs
(
obscfg
[
'
kind
'
],
time
,
n_obs
,
error_var
,
distance_between_obs_km
=
dist_obs
,
distance_between_obs_meters
,
fpath_obs_locations
=
fpath_obs_coords
)
output_path
=
cluster
.
dartrundir
,
fpath_obs_locations
=
cluster
.
archivedir
()
+
time
.
strftime
(
'
/%Y-%m-%d_%H:%M
'
)
if
obscfg
[
'
sat
'
]:
+
'
/obs_coords.pkl
'
)
osq
.
sat
(
time
,
sat_channel
,
obs_coords
,
error_var
,
set_input_nml
()
output_path
=
cluster
.
dartrundir
)
else
:
create_obsseq
.
sat
(
time
,
obscfg
[
'
channel
'
],
n_obs
,
error_var
,
distance_between_obs_meters
,
output_path
=
cluster
.
dartrundir
,
fpath_obs_locations
=
'
./domain.pkl
'
)
if
obscfg
[
'
channel
'
]
==
6
:
# for cloud dependent error
set_input_nml
(
sat_channel
=
obscfg
[
'
channel
'
],
just_prior_values
=
True
)
else
:
else
:
set_input_nml
(
sat_channel
=
obscfg
[
'
channel
'
])
osq
.
generic_obs
(
obscfg
[
'
kind
'
],
time
,
obs_coords
,
error_var
,
output_path
=
cluster
.
dartrundir
)
if
not
os
.
path
.
exists
(
cluster
.
dartrundir
+
'
/obs_seq.in
'
):
if
not
os
.
path
.
exists
(
cluster
.
dartrundir
+
'
/obs_seq.in
'
):
raise
RuntimeError
(
'
obs_seq.in does not exist in
'
+
cluster
.
dartrundir
)
raise
RuntimeError
(
'
obs_seq.in does not exist in
'
+
cluster
.
dartrundir
)
# generate observations (obs_seq.out)
# generate observations (obs_seq.out)
set_input_nml
(
sat_channel
=
sat_channel
,
cov_loc_radius_km
=
cov_loc
)
os
.
chdir
(
cluster
.
dartrundir
)
os
.
chdir
(
cluster
.
dartrundir
)
t
=
dt
.
datetime
.
now
()
t
=
dt
.
datetime
.
now
()
os
.
system
(
'
mpirun -np 12 ./perfect_model_obs
'
)
os
.
system
(
'
mpirun -np 12 ./perfect_model_obs
'
)
...
@@ -133,9 +134,9 @@ if __name__ == "__main__":
...
@@ -133,9 +134,9 @@ if __name__ == "__main__":
# cloud dependent observation error
# cloud dependent observation error
if
obscfg
[
'
sat
'
]:
if
obscfg
[
'
sat
'
]:
if
obscfg
[
'
channel
'
]
==
6
:
if
sat_
channel
==
6
:
# run ./filter to have prior observation estimates from model state
# run ./filter to have prior observation estimates from model state
set_input_nml
(
sat_channel
=
obscfg
[
'
channel
'
]
,
just_prior_values
=
True
)
set_input_nml
(
sat_channel
=
sat_
channel
,
just_prior_values
=
True
)
t
=
dt
.
datetime
.
now
()
t
=
dt
.
datetime
.
now
()
os
.
system
(
'
mv obs_seq.out obs_seq_all.out; mpirun -np 20 ./filter
'
)
os
.
system
(
'
mv obs_seq.out obs_seq_all.out; mpirun -np 20 ./filter
'
)
print
(
'
1st filter
'
,
(
dt
.
datetime
.
now
()
-
t
).
total_seconds
())
print
(
'
1st filter
'
,
(
dt
.
datetime
.
now
()
-
t
).
total_seconds
())
...
@@ -166,10 +167,12 @@ if __name__ == "__main__":
...
@@ -166,10 +167,12 @@ if __name__ == "__main__":
print
(
'
real obs gen
'
,
(
dt
.
datetime
.
now
()
-
t
).
total_seconds
())
print
(
'
real obs gen
'
,
(
dt
.
datetime
.
now
()
-
t
).
total_seconds
())
# correct input.nml for actual assimilation later on
# correct input.nml for actual assimilation later on
set_input_nml
(
sat_channel
=
obscfg
[
'
channel
'
],
just_prior_values
=
False
)
set_input_nml
(
sat_channel
=
sat_channel
,
cov_loc_radius_km
=
cov_loc
)
# rename according to i_obs
# rename according to i_obs
os
.
rename
(
cluster
.
dartrundir
+
'
/obs_seq.out
'
,
cluster
.
dartrundir
+
'
/obs_seq_
'
+
str
(
i_obs
)
+
'
.out
'
)
os
.
rename
(
cluster
.
dartrundir
+
'
/obs_seq.out
'
,
cluster
.
dartrundir
+
'
/obs_seq_
'
+
str
(
i_obs
)
+
'
.out
'
)
# concatenate the created obs_seq_*.out files
# concatenate the created obs_seq_*.out files
os
.
chdir
(
cluster
.
dartrundir
)
os
.
chdir
(
cluster
.
dartrundir
)
...
...
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment