each routine includes usual things it often has to do for subroutine-callable models which can manufacture an initial condition state vector. model_mod_check.f90 can be used to test these routines individually before you run it with filter. start with all defaults from other modules and add, in order the following routines:
1 | init_time() | |
2 | init_conditions() | for a "cold start" fill in an empty state vector with initial conditions and set the initial time. if the state vector is all 0s and the time is 0, you can use the default routines. |
3 | get_model_size() | return number of items in the state vector |
if you have only a single type of variable in your state vector, use the next two: | ||
4 | static_init_model() | often your model_size is set by namelist. allocate an array of that size and precompute all the locations for each state vector item. call add_domain() with the model size so dart knows how long the state vector is. |
5 | get_state_meta_data() | return QTY_STATE_VARIABLE as the quantity if present, and return the location for that index by looking it up in a location array. |
if you have more than a single type of variable in the state vector: | ||
4 | static_init_model() | read namelist to see how many fields are going to be read in for the state vector. use add_domain() to indicate which netcdf vars should be read. read in any auxiliary data needed by interpolation code (eg. topology). read template file to set grid locations. use get_domain_size() to compute model_size. |
5 | get_state_meta_data() | call get_model_variable_indices() and get_state_kind() to figure out the i,j,k indices and which variable this offset is. use the i,j,k to compute the grid location and return it along with the quantity. |
now continue | ||
6 | end_model() | deallocate any arrays allocated in static_init_model() |
at this point you can assimilate identity obs at the model time | ||
7 | adv_1step() | if possible, embed the code that computes x(t+1) = F(x(t)). or call a separate subroutine to advance the model state from one time to another. |
8 | shortest_time_between_assimilations() | return a namelist or a fixed value for the minimum model advance time. |
at this point you can assimilate a time series of identity obs | ||
9 | model_interpolate() | where the bulk of the work often is. this routine gets passed the location and quantity of the observation. find the indices which enclose that location and interpolate to get an array of expected values. |
at this point you can assimilate obs at locations other than state vector points. | ||
10 | nc_write_model_atts() | add attributes to the output diagnostic files. |
anything below here generally can use the default routines in other modules: | ||
11 | read_model_time() | |
12 | write_model_time() | generally can use the system defaults, unless you have a model restart file that already stores time in a particular format. |
13 | pert_model_copies() | the default is to add gaussian noise to the entire model state. if you want to only perturb a single variable, or perturb it with different noise ranges you can add code here. used to generate an ensemble from a single model state for filter. |
14 | convert_vertical_obs() | |
15 | convert_vertical_state() | unused in models without vertical coordinate choices |
16 | get_close_obs() | |
17 | get_close_state() | often unused unless you want to modify the localization behavior |
18 | nc_write_model_vars() | not currently called, leave it using the default routine. here for possible future implementation. |