LandscapeDNDC 1.37.0
ldndc::SoilChemistryMeTrX Class Reference

Biogeochemical model MeTrx. More...

#include <models/soilchemistry/metrx/soilchemistry-metrx.h>

Inherits ldndc::MBE_LegacyModel.

Public Member Functions

lerr_t solve ()
 

Private Member Functions

lerr_t MeTrX_write_output ()
 
lerr_t MeTrX_write_output_daily ()
 
lerr_t MeTrX_write_output_yearly ()
 
lerr_t MeTrX_write_output_layer_daily ()
 
lerr_t MeTrX_write_output_layer_yearly ()
 
lerr_t MeTrX_write_output_fluxes ()
 
lerr_t MeTrX_write_output_pools ()
 
lerr_t MeTrX_write_output_subdaily ()
 
lerr_t MeTrX_write_rates ()
 
lerr_t MeTrX_fertilize ()
 
lerr_t MeTrX_manure ()
 
lerr_t MeTrX_till ()
 
lerr_t MeTrX_reset ()
 
lerr_t MeTrX_reset_subdaily ()
 
lerr_t MeTrX_reset_daily ()
 
lerr_t MeTrX_update ()
 
lerr_t MeTrX_check_for_negative_value (char const *)
 iterates over complete soilchemistry state and checks for negative values
 
lerr_t MeTrX_spinup ()
 
lerr_t MeTrX_physics ()
 
void MeTrX_leaching ()
 Downwards transport of solutes, litter and humus with percolation water. More...
 
void MeTrX_groundwater_access ()
 
lerr_t MeTrX_plant_respiration (int)
 Updates o2 and co2 concentrations in soil layers. There is no o2 mass conservation guaranteed because vegetation modules calculate autotrophic respiration without oxygen limitation. When oxygen demand in soil layers is not fullfilled o2_deff stores deficit and increases oxygen demand in following layers.
 
lerr_t MeTrX_freeze_thaw ()
 
lerr_t MeTrX_radon_source_sink ()
 
lerr_t MeTrX_fragmentation ()
 
void MeTrX_litter_distribution (double const &, double const &, double const &, double const &, double const &, double const &, lvector< double > &accumulated_litter_sl)
 Adds carbon and nitrogen litter to soil litter pools.
 
lerr_t MeTrX_gas_diffusion ()
 
void MeTrX_liq_diffusion ()
 
lerr_t MeTrX_pertubation ()
 
lerr_t MeTrX_metabolism ()
 
lerr_t MeTrX_dissolution ()
 
void MeTrX_ebullition ()
 
void MeTrX_iron_reduction ()
 
void MeTrX_iron_oxidation ()
 
void MeTrX_algae_dynamics ()
 
void MeTrX_ch4_production ()
 
void MeTrX_ch4_oxidation ()
 
void MeTrX_microbial_dynamics ()
 
void MeTrX_soil_organic_matter_turnover ()
 
lerr_t MeTrX_fermentation ()
 
void MeTrX_urea_hydrolysis ()
 
void MeTrX_pH_calculation ()
 
lerr_t MeTrX_nitrogen_fertilizer_release ()
 Transforms nitrogen from slow release nitrogen fertilizer to nh4. More...
 
void MeTrX_nitrification ()
 
void MeTrX_denitrification ()
 
void MeTrX_chemodenitrification ()
 
void MeTrX_clay_nh4_equilibrium ()
 
void MeTrX_nh3_nh4_equilibrium ()
 
void MeTrX_anaerobic_volume ()
 
double MeTrX_get_ph_sl (size_t)
 Returns dynamic pH-value of given soil layer.
 
double MeTrX_get_ph_wl ()
 
double MeTrX_get_fact_tm_decomp (size_t const &)
 Response function for decomposition of organic matter depeding on temperature and moisture. More...
 
double MeTrX_get_fact_t_denit (size_t const &)
 The soil temperature response \( \phi_{T}\) of denitrification is given by the same temperature dependency as for general microbial activity: More...
 
double MeTrX_get_fact_m_denit (size_t const &)
 The soil moisture response \( \phi_{wfps}\) of denitrificstion is given by: More...
 
double MeTrX_get_fact_tm_denit (size_t const &)
 The temperature and moisture dependency of denitrifying microbes is given by the harmonic mean of a soil temperature ( \( \phi_{T}\)) and a soil moisture ( \( \phi_{wfps}\)) response coefficient. More...
 
double MeTrX_get_k_mm_x_sl (size_t const &_sl, double const &_k_mm)
 Scales Michaelis-Menten constant according to spatial discretization.
 
double MeTrX_get_c_tot ()
 
double MeTrX_get_n_tot ()
 
lerr_t MeTrX_receive_state ()
 
lerr_t MeTrX_send_state ()
 
lerr_t MeTrX_dissolution_soil (double const &, double &, double &)
 
lerr_t MeTrX_update_soil_discretization (bool)
 

Static Private Attributes

static const double TNORM = 293.2
 
static const double C_SATURATION = 82.0 * cbm::KG_IN_G
 

Detailed Description

Biogeochemical model MeTrx.

Member Function Documentation

◆ MeTrX_algae_dynamics()

void ldndc::SoilChemistryMeTrX::MeTrX_algae_dynamics ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_anaerobic_volume()

void ldndc::SoilChemistryMeTrX::MeTrX_anaerobic_volume ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_ch4_oxidation()

void ldndc::SoilChemistryMeTrX::MeTrX_ch4_oxidation ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_ch4_production()

void ldndc::SoilChemistryMeTrX::MeTrX_ch4_production ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_chemodenitrification()

void ldndc::SoilChemistryMeTrX::MeTrX_chemodenitrification ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_clay_nh4_equilibrium()

void ldndc::SoilChemistryMeTrX::MeTrX_clay_nh4_equilibrium ( )
private
Parameters
[in]None
[out]None
Returns
void
96{
97 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
98 {
99 /* partitioning coefficient */
100 double const k_nh4( 1.0);
101
102 /* total mount of n-nh4 [1e3:g] */
103 double const nh4_sol_old( nh4_ae_sl[sl] + nh4_an_sl[sl]);
104 double const nh4_total( nh4_sol_old + sc_.clay_nh4_sl[sl]);
105
106 /* soil mass [1e3:g] */
107 double const m_soil( sc_.get_soil_mass( sl));
108
109 /* soil organic matter content [%] */
110 double const som_percentage( sc_.som_sl[sl] / m_soil * 100.0);
111
112 /* cation exchange capacity [1e-2:mol] */
113 double const cec( cation_exchange_capacity(
114 sc_.clay_sl[sl] * 100.0,
115 sc_.sand_sl[sl] * 100.0,
116 som_percentage,
117 sc_.ph_sl[sl],
118 ECOSYS_GRASSLAND) * m_soil);
119
120 /* nh4 exchange capacity [kg] */
121 double const nh4_capacity( cec * cbm::MN * 1.0e-5);
122
123 /* nh4 per soil mass [1e-5:mol:g] */
124 double const nh4_total_percentage( nh4_total * 1.0e5 / (cbm::MN * m_soil));
125
126 /* adsorbed nh4 percentage [%] */
127 double const nh4_clay_percentage( k_nh4 * nh4_total_percentage);
128
129 /* adsorbed nh4 */
130 double const nh4_clay( cbm::bound_max( nh4_clay_percentage * 1.0e-2 * nh4_capacity, nh4_total));
131
132 /* nh4 - clay_nh4 exchange */
133 double const delta_nh4( cbm::flt_greater( nh4_clay, sc_.clay_nh4_sl[sl]) ?
134 (nh4_clay - sc_.clay_nh4_sl[sl]) * MeTrX_get_wfps( sl) * FTS_TOT_ :
135 (nh4_clay - sc_.clay_nh4_sl[sl]) * MeTrX_get_wfps( sl) * 0.1 * FTS_TOT_);
136
137 sc_.clay_nh4_sl[sl] += delta_nh4;
138 double const nh4_sol_new( nh4_total - sc_.clay_nh4_sl[sl]);
139 if ( cbm::flt_greater_zero( nh4_sol_old))
140 {
141 nh4_ae_sl[sl] = nh4_ae_sl[sl] / nh4_sol_old * nh4_sol_new;
142 nh4_an_sl[sl] = nh4_sol_new - nh4_ae_sl[sl];
143 }
144 else
145 {
146 nh4_ae_sl[sl] = nh4_sol_new * (1.0 - sc_.anvf_sl[sl]);
147 nh4_an_sl[sl] = nh4_sol_new * sc_.anvf_sl[sl];
148 }
149 }
150}
double LDNDC_API cation_exchange_capacity(double _clay, double _sand, double _som, double _ph, ecosystem_type_e _ecosystem)
Detailed description provided here .

References ldndc::cation_exchange_capacity().

Referenced by solve().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ MeTrX_denitrification()

void ldndc::SoilChemistryMeTrX::MeTrX_denitrification ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_dissolution()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_dissolution ( )
private
Parameters
[in]None
[out]None
Returns
error code

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_dissolution_soil()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_dissolution_soil ( double const &  _henry,
double &  _val_gas,
double &  _val_liq 
)
private
Parameters
[in]_henryNone
[in,out]_gasgaseous species
[in,out]_liqdissolved substance
Returns
error code
751{
752 double const val_tot( _val_gas + _val_liq);
753 if ( cbm::flt_greater_zero( val_tot))
754 {
755 _val_liq = _henry / (1.0 + _henry) * val_tot;
756 _val_gas = val_tot - _val_liq;
757 }
758 return LDNDC_ERR_OK;
759}

◆ MeTrX_ebullition()

void ldndc::SoilChemistryMeTrX::MeTrX_ebullition ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_fermentation()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_fermentation ( )
private
Parameters
[in]None
[out]None
Returns
error code

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_fertilize()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_fertilize ( )
private
Parameters
[in]None
[out]None
Returns
error code
34{
35 EventAttributes const * ev_fert = NULL;
36 while (( ev_fert = m_FertilizeEvents.pop()) != NULL)
37 {
38 double new_fertilizer_n( -sc_.accumulated_n_fertilizer);
39 //
40 cbm::string_t const fertilizer = ev_fert->get( "/type", "?");
41 //
42 double const f_depth = ev_fert->get( "/depth", 0.0);
43
44 // amount of fertilizer [kg:ha-1]
45 double const n_amount( ev_fert->get( "/amount", 0.0));
46
47 // amount of nitrification inhibitor [kg:ha-1]
48 double const ni_amount( ev_fert->get( "/ni_amount", 0.0));
49
50 // amount of urease inhibitor [kg:ha-1]
51 double const ui_amount( ev_fert->get( "/ui_amount", 0.0));
52
53 if ( have_water_table &&
54 cbm::flt_equal_zero( f_depth))
55 {
56 double const n_amount_sbl( n_amount / (cbm::M2_IN_HA * sb_.surfacebulk_layer_cnt()));
57 double const ni_amount_sbl( ni_amount / (cbm::M2_IN_HA * sb_.surfacebulk_layer_cnt()));
58 double const ui_amount_sbl( ui_amount / (cbm::M2_IN_HA * sb_.surfacebulk_layer_cnt()));
59
60 for (size_t sbl = 0; sbl < sb_.surfacebulk_layer_cnt(); ++sbl)
61 {
62 if ( fertilizer == "nh4no3" )
63 {
64 sb_.nh4_sbl[sbl] += 0.5 * n_amount_sbl;
65 sb_.no3_sbl[sbl] += 0.5 * n_amount_sbl;
66 accumulated_n_nh4_fertilization_sbl[sbl] += 0.5 * n_amount_sbl;
67 accumulated_n_no3_fertilization_sbl[sbl] += 0.5 * n_amount_sbl;
68 sc_.accumulated_n_fertilizer += n_amount_sbl;
69 }
70 else if ( fertilizer == "nh3" )
71 {
72 sb_.nh3_sbl[sbl] += n_amount_sbl;
73 accumulated_n_nh3_fertilization_sbl[sbl] += n_amount_sbl;
74 sc_.accumulated_n_fertilizer += n_amount_sbl;
75 }
76 else if ( fertilizer == "no3" )
77 {
78 sb_.no3_sbl[sbl] += n_amount_sbl;
79 accumulated_n_no3_fertilization_sbl[sbl] += n_amount_sbl;
80 sc_.accumulated_n_fertilizer += n_amount_sbl;
81 }
82 else if (( fertilizer == "nh4" ) || ( fertilizer == "nh4hco3" ) || ( fertilizer == "nh4hpo4" ))
83 {
84 sb_.nh4_sbl[sbl] += n_amount_sbl;
85 accumulated_n_nh4_fertilization_sbl[sbl] += n_amount_sbl;
86 sc_.accumulated_n_fertilizer += n_amount_sbl;
87 }
88 else if ( fertilizer == "nh4so4" )
89 {
90 sb_.so4_sbl[sbl] += n_amount_sbl * (cbm::MS / cbm::MN);
91 sb_.nh4_sbl[sbl] += n_amount_sbl;
92 accumulated_n_nh4_fertilization_sbl[sbl] += n_amount_sbl;
93 sc_.accumulated_n_fertilizer += n_amount_sbl;
94 }
95 else if ( fertilizer == "so4" )
96 {
97 sb_.so4_sbl[sbl] += n_amount_sbl;
98 }
99 else if ( fertilizer == "urea" )
100 {
101 sb_.urea_sbl[sbl] += n_amount_sbl;
102 accumulated_n_urea_fertilization_sbl[sbl] += n_amount_sbl;
103 sc_.accumulated_n_fertilizer += n_amount_sbl;
104 }
105 /* controled release nitrogen fertilizer */
106 else if ( fertilizer == "crnf" )
107 {
108 crnf_.add_crnf( n_amount_sbl);
109 sb_.coated_nh4_sbl[sbl] += n_amount_sbl;
110 sc_.accumulated_n_fertilizer += n_amount_sbl;
111 }
112 else
113 {
114 KLOGWARN( "Unknown fertilizer type \"",fertilizer,"\". Ignoring event!");
115 }
116
117 sb_.ni_sbl[sbl] += ni_amount_sbl;
118 sb_.ui_sbl[sbl] += ui_amount_sbl;
119 crnf_.add_nitrification_inhibitior( ni_amount_sbl);
120 crnf_.add_urease_inhibitior( ui_amount_sbl);
121 }
122 }
123 else
124 {
125 size_t l_0( 0);
126 size_t l_1( 1);
127 if ( cbm::flt_equal_zero( f_depth))
128 {
129 l_0 = 0;
130 l_1 = 1;
131 for( size_t sl = 1; sl < sl_.soil_layer_cnt(); ++sl)
132 {
133 if ( sc_.depth_sl[sl] <= 0.01)
134 {
135 l_1 = sl;
136 }
137 else{ break; }
138 }
139 }
140 else
141 {
142 //l_0 not allowed to be deeper than last but one soil layer
143 l_0 = sl_.soil_layer_cnt()-2;
144 //find first layer (from top) having at least depth <depth(fert)>
145 for ( size_t l = 0; l < sl_.soil_layer_cnt()-1; ++l)
146 {
147 if ( cbm::flt_greater_equal( sc_.depth_sl[l], f_depth))
148 {
149 l_0 = l;
150 break;
151 }
152 }
153 //l_1 must at least one layer below l_0
154 l_1 = l_0 + 1;
155 for ( size_t l = l_0 + 1; l < sl_.soil_layer_cnt(); ++l)
156 {
157 /* distribute at least among 4cm soil profile */
158 if ( cbm::flt_greater_equal( sc_.depth_sl[l], f_depth + 0.04))
159 {
160 l_1 = l;
161 break;
162 }
163 }
164 }
165
166 double const n_amount_per_layer = (n_amount / cbm::M2_IN_HA) / (double)( l_1 - l_0);
167 double const ni_amount_per_layer = (ni_amount / cbm::M2_IN_HA) / (double)( l_1 - l_0);
168 double const ui_amount_per_layer = (ui_amount / cbm::M2_IN_HA) / (double)( l_1 - l_0);
169
170 for ( size_t sl = l_0; sl < l_1; ++sl)
171 {
172 if ( fertilizer == "nh4no3" )
173 {
174 nh4_ae_sl[sl] += 0.5 * n_amount_per_layer * (1.0 - sc_.anvf_sl[sl]);
175 nh4_an_sl[sl] += 0.5 * n_amount_per_layer * sc_.anvf_sl[sl];
176 no3_ae_sl[sl] += 0.5 * n_amount_per_layer * (1.0 - sc_.anvf_sl[sl]);
177 no3_an_sl[sl] += 0.5 * n_amount_per_layer * sc_.anvf_sl[sl];
178 accumulated_n_nh4_fertilization_sl[sl] += 0.5 * n_amount_per_layer;
179 accumulated_n_no3_fertilization_sl[sl] += 0.5 * n_amount_per_layer;
180 sc_.accumulated_n_fertilizer += n_amount_per_layer;
181 }
182 else if ( fertilizer == "nh3" )
183 {
184 sc_.nh3_liq_sl[sl] += n_amount_per_layer;
185 accumulated_n_nh3_fertilization_sl[sl] += n_amount_per_layer;
186 sc_.accumulated_n_fertilizer += n_amount_per_layer;
187 }
188 else if ( fertilizer == "no3" )
189 {
190 no3_ae_sl[sl] += n_amount_per_layer * (1.0 - sc_.anvf_sl[sl]);
191 no3_an_sl[sl] += n_amount_per_layer * sc_.anvf_sl[sl];
192 accumulated_n_no3_fertilization_sl[sl] += n_amount_per_layer;
193 sc_.accumulated_n_fertilizer += n_amount_per_layer;
194 }
195 else if (( fertilizer == "nh4" ) || ( fertilizer == "nh4hco3" ) || ( fertilizer == "nh4hpo4" ))
196 {
197 nh4_ae_sl[sl] += n_amount_per_layer * (1.0 - sc_.anvf_sl[sl]);
198 nh4_an_sl[sl] += n_amount_per_layer * sc_.anvf_sl[sl];
199 accumulated_n_nh4_fertilization_sl[sl] += n_amount_per_layer;
200 sc_.accumulated_n_fertilizer += n_amount_per_layer;
201 }
202 else if ( fertilizer == "nh4so4" )
203 {
204 sc_.so4_sl[sl] += n_amount_per_layer * (cbm::MS / cbm::MN);
205 nh4_ae_sl[sl] += n_amount_per_layer * (1.0 - sc_.anvf_sl[sl]);
206 nh4_an_sl[sl] += n_amount_per_layer * sc_.anvf_sl[sl];
207 accumulated_n_nh4_fertilization_sl[sl] += n_amount_per_layer;
208 sc_.accumulated_n_fertilizer += n_amount_per_layer;
209 }
210 else if ( fertilizer == "so4" )
211 {
212 sc_.so4_sl[sl] += n_amount_per_layer;
213 }
214 else if ( fertilizer == "urea" )
215 {
216 sc_.urea_sl[sl] += n_amount_per_layer;
217 accumulated_n_urea_fertilization_sl[sl] += n_amount_per_layer;
218 sc_.accumulated_n_fertilizer += n_amount_per_layer;
219 }
220 /* controled release nitrogen fertilizer */
221 else if ( fertilizer == "crnf" )
222 {
223 crnf_.add_crnf( n_amount_per_layer);
224 sc_.coated_nh4_sl[sl] += n_amount_per_layer;
225 accumulated_n_nh4_fertilization_sl[sl] += n_amount_per_layer;
226 sc_.accumulated_n_fertilizer += n_amount_per_layer;
227 }
228 else
229 {
230 KLOGWARN( "Unknown fertilizer type \"",fertilizer,"\". Skipping event!");
231 break;
232 }
233
234 sc_.ni_sl[sl] += ni_amount_per_layer;
235 sc_.ui_sl[sl] += ui_amount_per_layer;
236 crnf_.add_nitrification_inhibitior( ni_amount_per_layer);
237 crnf_.add_urease_inhibitior( ui_amount_per_layer);
238 }
239 }
240
241 cbm::state_scratch_t * mcom = io_kcomm->get_scratch();
242
243 new_fertilizer_n += sc_.accumulated_n_fertilizer;
244 double old_fertilizer_n( 0.0);
245 mcom->get( "fertilize:amount", &old_fertilizer_n, 0.0);
246 mcom->set( "fertilize:amount", old_fertilizer_n + (new_fertilizer_n * cbm::M2_IN_HA));
247 }
248
249 return LDNDC_ERR_OK;
250}

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_fragmentation()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_fragmentation ( )
private
Parameters
[in]None
[out]None
Returns
error code
25{
26 /* wood / stubble / ... -> raw litter */
27
28 //rough estimates of dead wood constituents
29 double const extractives_wood( 0.05);
30 double const cellulose_wood( 0.60); // including hemicellulose
31 double const lignin_wood( 0.35);
32
33 /* aboveground wood litter */
34 if ( cbm::flt_greater_zero( sc_.c_wood) ||
35 cbm::flt_greater_zero( sc_.n_wood))
36 {
37 double const k_frag_wood_tm( K_FRAG_WOOD * MeTrX_get_fact_tm_decomp( 0));
38 double const frag_c_wood( k_frag_wood_tm * sc_.c_wood);
39 double const frag_n_wood( k_frag_wood_tm * sc_.n_wood);
40
41 sc_.c_wood -= frag_c_wood;
42 sc_.n_wood -= frag_n_wood;
43
44 sc_.c_raw_lit_1_above += extractives_wood * frag_c_wood;
45 sc_.c_raw_lit_2_above += cellulose_wood * frag_c_wood;
46 sc_.c_raw_lit_3_above += lignin_wood * frag_c_wood;
47
48 sc_.n_raw_lit_1_above += extractives_wood * frag_n_wood;
49 sc_.n_raw_lit_2_above += cellulose_wood * frag_n_wood;
50 sc_.n_raw_lit_3_above += lignin_wood * frag_n_wood;
51
52 if ( spinup_.spinup_stage( this->lclock()))
53 {
54 spinup_.exit_wood += frag_c_wood;
55 }
56 }
57
58 /* belowground wood litter */
59 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
60 {
61 if ( cbm::flt_greater_zero( sc_.c_wood_sl[sl]) ||
62 cbm::flt_greater_zero( sc_.n_wood_sl[sl]))
63 {
64 double const k_frag_wood_tm( K_FRAG_WOOD * MeTrX_get_fact_tm_decomp( sl));
65 double const frag_c_wood( k_frag_wood_tm * sc_.c_wood_sl[sl]);
66 double const frag_n_wood( k_frag_wood_tm * sc_.n_wood_sl[sl]);
67
68 sc_.c_wood_sl[sl] -= frag_c_wood;
69 sc_.n_wood_sl[sl] -= frag_n_wood;
70
71 sc_.c_raw_lit_1_sl[sl] += extractives_wood * frag_c_wood;
72 sc_.c_raw_lit_2_sl[sl] += cellulose_wood * frag_c_wood;
73 sc_.c_raw_lit_3_sl[sl] += lignin_wood * frag_c_wood;
74
75 sc_.n_raw_lit_1_sl[sl] += extractives_wood * frag_n_wood;
76 sc_.n_raw_lit_2_sl[sl] += cellulose_wood * frag_n_wood;
77 sc_.n_raw_lit_3_sl[sl] += lignin_wood * frag_n_wood;
78 }
79 }
80
81
82 /* stubble litter */
83 if ( cbm::flt_greater_zero( sc_.c_stubble_lit1 + sc_.c_stubble_lit2 + sc_.c_stubble_lit3))
84 {
85 double const k_frag_stubble_tm( K_FRAG_STUBBLE * MeTrX_get_fact_tm_decomp( 0));
86 double const c_senescence_lit1( k_frag_stubble_tm * sc_.c_stubble_lit1);
87 double const c_senescence_lit2( k_frag_stubble_tm * sc_.c_stubble_lit2);
88 double const c_senescence_lit3( k_frag_stubble_tm * sc_.c_stubble_lit3);
89
90 double const n_senescence_lit1( k_frag_stubble_tm * sc_.n_stubble_lit1);
91 double const n_senescence_lit2( k_frag_stubble_tm * sc_.n_stubble_lit2);
92 double const n_senescence_lit3( k_frag_stubble_tm * sc_.n_stubble_lit3);
93
94 sc_.c_stubble_lit1 -= c_senescence_lit1;
95 sc_.c_stubble_lit2 -= c_senescence_lit2;
96 sc_.c_stubble_lit3 -= c_senescence_lit3;
97
98 sc_.n_stubble_lit1 -= n_senescence_lit1;
99 sc_.n_stubble_lit2 -= n_senescence_lit2;
100 sc_.n_stubble_lit3 -= n_senescence_lit3;
101
102 sc_.c_raw_lit_1_above += c_senescence_lit1;
103 sc_.c_raw_lit_2_above += c_senescence_lit2;
104 sc_.c_raw_lit_3_above += c_senescence_lit3;
105
106 sc_.n_raw_lit_1_above += n_senescence_lit1;
107 sc_.n_raw_lit_2_above += n_senescence_lit2;
108 sc_.n_raw_lit_3_above += n_senescence_lit3;
109 }
110
111
112 /* algae / dung / raw litter -> soil litter */
113
114 /* algae litter */
115 if ( cbm::flt_greater_zero( c_dead_algae) ||
116 cbm::flt_greater_zero( n_dead_algae))
117 {
118 //rough estimates of algae constituents
119 double const extractives_algae( 0.25);
120 double const cellulose_algae( 0.70); // including hemicellulose
121 double const lignin_algae( 0.05);
122
123 double const fact_decomp( K_FRAG_ALGAE * MeTrX_get_fact_tm_decomp( 0));
124 double const c_decomp_algae( fact_decomp * c_dead_algae);
125 double const n_decomp_algae( fact_decomp * n_dead_algae);
126
127 c_dead_algae -= c_decomp_algae;
128 n_dead_algae -= n_decomp_algae;
129
130 MeTrX_litter_distribution( extractives_algae * n_decomp_algae, cellulose_algae * n_decomp_algae, lignin_algae * n_decomp_algae,
131 extractives_algae * c_decomp_algae, cellulose_algae * c_decomp_algae, lignin_algae * c_decomp_algae,
132 accumulated_n_litter_from_algae_sl);
133
134 dC_litter_algae += c_decomp_algae;
135
136 if ( !cbm::flt_greater_zero( c_dead_algae))
137 {
138 c_dead_algae = 0.0;
139 }
140 if ( !cbm::flt_greater_zero( n_dead_algae))
141 {
142 n_dead_algae = 0.0;
143 }
144 }
145
146 /* dung and urine */
147 if ( cbm::flt_greater_zero( sc_.c_dung) ||
148 cbm::flt_greater_zero( sc_.n_dung) ||
149 cbm::flt_greater_zero( sc_.n_urine))
150 {
151 MeTrX_litter_distribution( 0.25 * sc_.n_dung, 0.7 * sc_.n_dung, 0.05 * sc_.n_dung,
152 0.25 * sc_.c_dung, 0.7 * sc_.c_dung, 0.05 * sc_.c_dung,
153 accumulated_n_litter_from_dung_sl);
154
155 for( size_t sl = 0; sl <= SL_SURFACE_DISTRIBUTION; ++sl)
156 {
157 sc_.urea_sl[sl] += sc_.n_urine * SL_SURFACE_DISTRIBUTION_INVERSE;
158 accumulated_n_urea_from_dung_sl[sl] += sc_.n_urine * SL_SURFACE_DISTRIBUTION_INVERSE;
159 }
160
161 sc_.accumulated_c_livestock_grazing += sc_.c_dung;
162 sc_.accumulated_n_livestock_grazing += sc_.n_dung + sc_.n_urine;
163
164 sc_.c_dung = 0.0;
165 sc_.n_dung = 0.0;
166 sc_.n_urine = 0.0;
167 }
168
169 /* aboveground raw litter */
170 if ( cbm::flt_greater_zero( sc_.c_raw_lit_1_above + sc_.c_raw_lit_2_above + sc_.c_raw_lit_3_above))
171 {
172 double const k_frag_raw_litter_tm( K_FRAG_RAW_LITTER * MeTrX_get_fact_tm_decomp( 0));
173 double const c_senescence_lit1( k_frag_raw_litter_tm * sc_.c_raw_lit_1_above);
174 double const c_senescence_lit2( k_frag_raw_litter_tm * sc_.c_raw_lit_2_above);
175 double const c_senescence_lit3( k_frag_raw_litter_tm * sc_.c_raw_lit_3_above);
176
177 double const n_senescence_lit1( k_frag_raw_litter_tm * sc_.n_raw_lit_1_above);
178 double const n_senescence_lit2( k_frag_raw_litter_tm * sc_.n_raw_lit_2_above);
179 double const n_senescence_lit3( k_frag_raw_litter_tm * sc_.n_raw_lit_3_above);
180
181 sc_.c_raw_lit_1_above -= c_senescence_lit1;
182 sc_.c_raw_lit_2_above -= c_senescence_lit2;
183 sc_.c_raw_lit_3_above -= c_senescence_lit3;
184
185 sc_.n_raw_lit_1_above -= n_senescence_lit1;
186 sc_.n_raw_lit_2_above -= n_senescence_lit2;
187 sc_.n_raw_lit_3_above -= n_senescence_lit3;
188
189 MeTrX_litter_distribution( n_senescence_lit1, n_senescence_lit2, n_senescence_lit3,
190 c_senescence_lit1, c_senescence_lit2, c_senescence_lit3,
191 accumulated_n_aboveground_raw_litter_fragmentation_sl);
192 }
193
194 /* belowground raw litter */
195 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
196 {
197 double const c_raw_litter_tot( sc_.c_raw_lit_1_sl[sl] + sc_.c_raw_lit_2_sl[sl] + sc_.c_raw_lit_3_sl[sl]);
198 if ( cbm::flt_greater_zero( c_raw_litter_tot))
199 {
200 double const fact_decomp( K_FRAG_RAW_LITTER * MeTrX_get_fact_tm_decomp( sl));
201 double const c_decomp_lit1( fact_decomp * sc_.c_raw_lit_1_sl[sl]);
202 double const c_decomp_lit2( fact_decomp * sc_.c_raw_lit_2_sl[sl]);
203 double const c_decomp_lit3( fact_decomp * sc_.c_raw_lit_3_sl[sl]);
204
205 double const n_decomp_lit1( fact_decomp * sc_.n_raw_lit_1_sl[sl]);
206 double const n_decomp_lit2( fact_decomp * sc_.n_raw_lit_2_sl[sl]);
207 double const n_decomp_lit3( fact_decomp * sc_.n_raw_lit_3_sl[sl]);
208
209 sc_.c_raw_lit_1_sl[sl] -= c_decomp_lit1;
210 sc_.c_raw_lit_2_sl[sl] -= c_decomp_lit2;
211 sc_.c_raw_lit_3_sl[sl] -= c_decomp_lit3;
212
213 sc_.n_raw_lit_1_sl[sl] -= n_decomp_lit1;
214 sc_.n_raw_lit_2_sl[sl] -= n_decomp_lit2;
215 sc_.n_raw_lit_3_sl[sl] -= n_decomp_lit3;
216
217 sc_.C_lit1_sl[sl] += c_decomp_lit1;
218 sc_.C_lit2_sl[sl] += c_decomp_lit2;
219 sc_.C_lit3_sl[sl] += c_decomp_lit3;
220
221 sc_.N_lit1_sl[sl] += n_decomp_lit1;
222 sc_.N_lit2_sl[sl] += n_decomp_lit2;
223 sc_.N_lit3_sl[sl] += n_decomp_lit3;
224
225 accumulated_n_belowground_raw_litter_fragmentation_sl[sl] += n_decomp_lit1 + n_decomp_lit2 + n_decomp_lit3;
226
227 if ( spinup_.spinup_stage( this->lclock()))
228 {
229 spinup_.c_to_lit_1[sl] += c_decomp_lit1;
230 spinup_.c_to_lit_2[sl] += c_decomp_lit2;
231 spinup_.c_to_lit_3[sl] += c_decomp_lit3;
232 }
233 }
234 }
235
236 return LDNDC_ERR_OK;
237}
void MeTrX_litter_distribution(double const &, double const &, double const &, double const &, double const &, double const &, lvector< double > &accumulated_litter_sl)
Adds carbon and nitrogen litter to soil litter pools.
Definition: soilchemistry-metrx-fragmentation.cpp:245
double MeTrX_get_fact_tm_decomp(size_t const &)
Response function for decomposition of organic matter depeding on temperature and moisture.
Definition: soilchemistry-metrx-decomposition.cpp:689

References MeTrX_get_fact_tm_decomp(), and MeTrX_litter_distribution().

Referenced by solve().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ MeTrX_freeze_thaw()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_freeze_thaw ( )
private
Parameters
[in]None
[out]None
Returns
error code
410{
411 if ( (freeze_thaw_method == "ft_processes") || (freeze_thaw_method == "yes"))
412 {
413 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
414 {
415 // ICE + NEG. TEMP.
416 if ( cbm::flt_greater_zero( v_ice_sl[sl]) &&
417 cbm::flt_less_equal( mc_temp_sl[sl], 0.0))
418 {
419 cumulative_freezing_degree_days_sl[sl] += std::abs( mc_temp_sl[sl]) * FTS_TOT_;
420 if ( cbm::flt_less_equal( mc_temp_sl[sl], -sipar_.METRX_CFDD_THRESHOLD()))
421 {
422 cfdd_turnover_sl[sl] += std::abs( mc_temp_sl[sl]) * FTS_TOT_;
423 }
424 }
425 else if ( cbm::flt_greater_equal( mc_temp_sl[sl], 0.0))
426 {
427 if ( cbm::flt_greater( cfdd_turnover_sl[sl], sipar_.METRX_CFDD_MIN()))
428 {
429 // linear function
430 // double c_decomp_aorg(cbm::bound(0.0, cfdd_turnover_sl[sl] / sipar_.METRX_CFDD_MAX(), 0.99) * sc_.C_aorg_sl[sl] * sipar_.METRX_CFDD_TURN_MAX());
431 // double n_decomp_aorg(cbm::bound(0.0, cfdd_turnover_sl[sl] / sipar_.METRX_CFDD_MAX(), 0.99) * sc_.N_aorg_sl[sl] * sipar_.METRX_CFDD_TURN_MAX());
432 // saturation function
433 double c_decomp_aorg( cbm::bound( 0.0, 1.0 /(1.0+ std::exp(-0.05 * (cfdd_turnover_sl[sl] - (sipar_.METRX_CFDD_MAX()/2.0)))), 0.99) * sc_.C_aorg_sl[sl] * sipar_.METRX_CFDD_TURN_MAX());
434 double n_decomp_aorg( cbm::bound( 0.0, 1.0 /(1.0+ std::exp(-0.05 * (cfdd_turnover_sl[sl] - (sipar_.METRX_CFDD_MAX()/2.0)))), 0.99) * sc_.N_aorg_sl[sl] * sipar_.METRX_CFDD_TURN_MAX());
435
436 sc_.C_aorg_sl[sl] -= c_decomp_aorg;
437 sc_.N_aorg_sl[sl] -= n_decomp_aorg;
438
439 sc_.an_doc_sl[sl] += c_decomp_aorg * sc_.anvf_sl[sl];
440 sc_.doc_sl[sl] += c_decomp_aorg * (1.0 - sc_.anvf_sl[sl]);
441
442 don_ae_sl[sl] += (1.0 - sipar_.METRX_FRAC_MINERAL()) * n_decomp_aorg * (1.0 - sc_.anvf_sl[sl]);
443 don_an_sl[sl] += (1.0 - sipar_.METRX_FRAC_MINERAL()) * n_decomp_aorg * sc_.anvf_sl[sl];
444
445 nh4_ae_sl[sl] += sipar_.METRX_FRAC_MINERAL() * n_decomp_aorg * (1.0 - sc_.anvf_sl[sl]);
446 nh4_an_sl[sl] += sipar_.METRX_FRAC_MINERAL() * n_decomp_aorg * sc_.anvf_sl[sl];
447 }
448
449 cumulative_freezing_degree_days_sl[sl] = 0.0;
450 cfdd_turnover_sl[sl] = 0.0;
451 }
452 }
453 }
454
455 return LDNDC_ERR_OK;
456}

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_gas_diffusion()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_gas_diffusion ( )
private
Parameters
[in]None
[out]None
Returns
error code

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_get_c_tot()

double ldndc::SoilChemistryMeTrX::MeTrX_get_c_tot ( )
private
Parameters
[in]None
[out]None
Returns
Total soil associated carbon
62{
63 double c_tot( c_algae + c_dead_algae + sc_.c_wood
64 + sc_.c_stubble_lit1 + sc_.c_stubble_lit2 + sc_.c_stubble_lit3
65 + sc_.c_raw_lit_1_above + sc_.c_raw_lit_2_above + sc_.c_raw_lit_3_above);
66
67 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
68 {
69 c_tot += ( sc_.c_wood_sl[sl]
70 + sc_.doc_sl[sl] + sc_.an_doc_sl[sl] + doc_ice_sl[sl]
71 + ae_acetate_sl[sl] + an_acetate_sl[sl] + acetate_ice_sl[sl]
72 + sc_.C_micro1_sl[sl] + sc_.C_micro2_sl[sl] + sc_.C_micro3_sl[sl]
73 + sc_.C_aorg_sl[sl] + c_microbial_necromass_sl[sl]
74 + c_humus_1_sl[sl] + c_humus_2_sl[sl] + c_humus_3_sl[sl]
75 + sc_.C_lit1_sl[sl] + sc_.C_lit2_sl[sl] + sc_.C_lit3_sl[sl]
76 + sc_.c_raw_lit_1_sl[sl] + sc_.c_raw_lit_2_sl[sl] + sc_.c_raw_lit_3_sl[sl]
77 + ch4_gas_sl[sl] + ch4_liq_sl[sl]
78 + co2_gas_sl[sl] + co2_liq_sl[sl]);
79 }
80
81 for (size_t sbl = 0; sbl < sb_.surfacebulk_layer_cnt(); ++sbl)
82 {
83 c_tot += sb_.ch4_sbl[sbl] + sb_.co2_sbl[sbl] + sb_.doc_sbl[sbl];
84 }
85
86 return c_tot;
87}

◆ MeTrX_get_fact_m_denit()

double ldndc::SoilChemistryMeTrX::MeTrX_get_fact_m_denit ( size_t const &  _sl)
private

The soil moisture response \( \phi_{wfps}\) of denitrificstion is given by:

\[ \phi_{wfps} = 1 - \frac{1}{1 + e^{(wfps - \Omega_{MFDMW1}) \cdot \Omega_{MFDMW2}}} \]

  • \( \Omega_{MFDMW1} \): METRX_F_DENIT_M_WEIBULL_1
  • \( \Omega_{MFDMW2} \): METRX_F_DENIT_M_WEIBULL_2
Response function depending on soilwater
533{
534 return ldndc::meteo::F_weibull( MeTrX_get_wfps_eff( _sl, 0.0),
535 sipar_.METRX_F_DENIT_M_WEIBULL_1(),
536 sipar_.METRX_F_DENIT_M_WEIBULL_2(),
537 1.0);
538}

Referenced by MeTrX_get_fact_tm_denit().

Here is the caller graph for this function:

◆ MeTrX_get_fact_t_denit()

double ldndc::SoilChemistryMeTrX::MeTrX_get_fact_t_denit ( size_t const &  _sl)
private

The soil temperature response \( \phi_{T}\) of denitrification is given by the same temperature dependency as for general microbial activity:

\[ \phi_{T} = e^{-\Omega_{MFMTE1} \cdot \left( 1 - \frac{T}{\Omega_{MFMTE2}} \right)^2} \]

  • \( \Omega_{MFMTE1} \): METRX_F_MIC_T_EXP_1
  • \( \Omega_{MFMTE2} \): METRX_F_MIC_T_EXP_2
Response function depending on temperature
501{
502 double const help( std::pow(1.0 - mc_temp_sl[_sl] / sipar_.METRX_F_MIC_T_EXP_2(), 2.0));
503 // modification of temp.-dependency of denitrifying microbes
504 if ( freeze_thaw_method == "ft_processes")
505 {
506 return std::exp( -(sipar_.METRX_F_MIC_T_EXP_COLD() +
507 (sipar_.METRX_F_MIC_T_EXP_1() - sipar_.METRX_F_MIC_T_EXP_COLD()) /
508 (1.0 + std::exp(-sipar_.METRX_F_MIC_T_EXP_1() *
509 (mc_temp_sl[_sl] - sipar_.METRX_F_MIC_T_EXP_2())))) * help);
510 }
511 else
512 {
513 return std::exp( -sipar_.METRX_F_MIC_T_EXP_1() * help);
514 }
515}

Referenced by MeTrX_get_fact_tm_denit().

Here is the caller graph for this function:

◆ MeTrX_get_fact_tm_decomp()

double ldndc::SoilChemistryMeTrX::MeTrX_get_fact_tm_decomp ( size_t const &  _sl)
private

Response function for decomposition of organic matter depeding on temperature and moisture.

Parameters
[in]_slsoil layer
[out]None
Returns
requested factor
690{
691 double const fact_t( std::exp( -sipar_.METRX_F_DECOMP_T_EXP_1() *
692 pow(1.0 - mc_temp_sl[_sl] / sipar_.METRX_F_DECOMP_T_EXP_2(), 2.0)));
693 double const fact_m( ldndc::meteo::F_weibull( MeTrX_get_wfps_eff( _sl, 0.0),
694 sipar_.METRX_F_DECOMP_M_WEIBULL_1(),
695 sipar_.METRX_F_DECOMP_M_WEIBULL_2(),
696 1.0));
697 return cbm::harmonic_mean2( fact_t, fact_m);
698}

Referenced by MeTrX_fragmentation().

Here is the caller graph for this function:

◆ MeTrX_get_fact_tm_denit()

double ldndc::SoilChemistryMeTrX::MeTrX_get_fact_tm_denit ( size_t const &  _sl)
private

The temperature and moisture dependency of denitrifying microbes is given by the harmonic mean of a soil temperature ( \( \phi_{T}\)) and a soil moisture ( \( \phi_{wfps}\)) response coefficient.

\[ \frac{2}{\frac{1}{\phi_{T}} + \frac{1}{\phi_{wfps}}} \]

The soil temperature response \( \phi_{T}\) of denitrification is given by the same temperature dependency as for general microbial activity:

\[ \phi_{T} = e^{-\Omega_{MFMTE1} \cdot \left( 1 - \frac{T}{\Omega_{MFMTE2}} \right)^2} \]

  • \( \Omega_{MFMTE1} \): METRX_F_MIC_T_EXP_1
  • \( \Omega_{MFMTE2} \): METRX_F_MIC_T_EXP_2
Response function depending on temperature

The soil moisture response \( \phi_{wfps}\) of denitrificstion is given by:

\[ \phi_{wfps} = 1 - \frac{1}{1 + e^{(wfps - \Omega_{MFDMW1}) \cdot \Omega_{MFDMW2}}} \]

  • \( \Omega_{MFDMW1} \): METRX_F_DENIT_M_WEIBULL_1
  • \( \Omega_{MFDMW2} \): METRX_F_DENIT_M_WEIBULL_2
Response function depending on soilwater
556{
557 return cbm::harmonic_mean2( MeTrX_get_fact_t_denit( _sl),
559}
double MeTrX_get_fact_m_denit(size_t const &)
The soil moisture response of denitrificstion is given by:
Definition: soilchemistry-metrx-denitrification.cpp:532
double MeTrX_get_fact_t_denit(size_t const &)
The soil temperature response of denitrification is given by the same temperature dependency as for ...
Definition: soilchemistry-metrx-denitrification.cpp:500

References MeTrX_get_fact_m_denit(), and MeTrX_get_fact_t_denit().

Here is the call graph for this function:

◆ MeTrX_get_n_tot()

double ldndc::SoilChemistryMeTrX::MeTrX_get_n_tot ( )
private
Parameters
[in]None
[out]None
Returns
Total soil associated nitrogen
19{
20 double n_tot( n_algae + n_dead_algae + sc_.n_wood
21 + sc_.n_stubble_lit1 + sc_.n_stubble_lit2 + sc_.n_stubble_lit3
22 + sc_.n_raw_lit_1_above + sc_.n_raw_lit_2_above + sc_.n_raw_lit_3_above);
23
24 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
25 {
26 n_tot += ( sc_.n_wood_sl[sl]
27 + nh4_ae_sl[sl] + nh4_an_sl[sl] + sc_.clay_nh4_sl[sl] + sc_.coated_nh4_sl[sl] + nh4_ice_sl[sl]
28 + sc_.nh3_liq_sl[sl] + sc_.nh3_gas_sl[sl] + sc_.urea_sl[sl]
29 + no3_ae_sl[sl] + no3_an_sl[sl] + no3_ice_sl[sl]
30 + sc_.no2_sl[sl] + sc_.an_no2_sl[sl]
31 + don_ae_sl[sl] + don_an_sl[sl] + don_ice_sl[sl]
32 + no_gas_sl[sl] + an_no_gas_sl[sl] + no_liq_sl[sl] + an_no_liq_sl[sl]
33 + n2o_gas_sl[sl] + an_n2o_gas_sl[sl] + n2o_liq_sl[sl] + an_n2o_liq_sl[sl]
34 + sc_.N_lit1_sl[sl] + sc_.N_lit2_sl[sl] + sc_.N_lit3_sl[sl]
35 + sc_.n_raw_lit_1_sl[sl] + sc_.n_raw_lit_2_sl[sl] + sc_.n_raw_lit_3_sl[sl]
36 + n_micro_1_sl[sl] + n_micro_2_sl[sl] + n_micro_3_sl[sl]
37 + sc_.N_aorg_sl[sl] + n_microbial_necromass_sl[sl]
38 + n_humus_1_sl[sl] + n_humus_2_sl[sl] + n_humus_3_sl[sl]);
39 }
40
41 for (size_t sbl = 0; sbl < sb_.surfacebulk_layer_cnt(); ++sbl)
42 {
43 n_tot += sb_.nh4_sbl[sbl] + sb_.coated_nh4_sbl[sbl]
44 + sb_.no3_sbl[sbl] + sb_.don_sbl[sbl]
45 + sb_.nh3_sbl[sbl] + sb_.urea_sbl[sbl]
46 + sb_.n2o_sbl[sbl] + sb_.no_sbl[sbl];
47 }
48
49 n_tot += nh3_fl.sum();
50
51 return n_tot;
52}

◆ MeTrX_get_ph_wl()

double ldndc::SoilChemistryMeTrX::MeTrX_get_ph_wl ( )
private
Parameters
[in]None
[out]None
Returns
double
608{
609 if ( cbm::flt_greater_zero( wc_.surface_water))
610 {
611 return cbm::bound( PH_SURFACE_WATER, PH_SURFACE_WATER + ph_delta_pab_wl + ph_delta_urea_wl, PH_MAX);
612 }
613 else
614 {
615 return 7.0;
616 }
617}

Referenced by MeTrX_nh3_nh4_equilibrium(), MeTrX_write_output_daily(), MeTrX_write_output_layer_daily(), and MeTrX_write_output_subdaily().

Here is the caller graph for this function:

◆ MeTrX_groundwater_access()

void ldndc::SoilChemistryMeTrX::MeTrX_groundwater_access ( )
private
Parameters
[in]None
[out]None
Returns
void
  • exchange of soil no3 <-> groundwater no3
  • only calculated in case of valid groundwater input
769{
770 if ( gw_ != NULL)
771 {
772 for ( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
773 {
774 if ( sc_.depth_sl[sl] > gw_->watertable_subday( lclock_ref()))
775 {
776 double const no3_gw( gw_->no3_day(lclock_ref()) //given in (mg no3 L-1)
777 * cbm::MN / (cbm::MN + 3.0 * cbm::MO) * cbm::KG_IN_MG //converts no3 from (mg no3) -> (kg n-no3)
778 * (wc_.wc_sl[sl] + wc_.ice_sl[sl]) * sc_.h_sl[sl] * cbm::DM3_IN_M3); //converts water (m3) -> (L)
779
780 if ( cbm::flt_greater_zero( no3_gw))
781 {
782 double const no3_diff( GROUNDWATER_NUTRIENT_ACCESS_RATE * (no3_gw - no3_an_sl[sl]));
783 no3_an_sl[sl] += no3_diff;
784 day_no3_groundwater_access += no3_diff;
785 sc_.accumulated_no3_leach -= no3_diff;
786 sc_.accumulated_n_no3_leaching_sl[sl] -= no3_diff;
787 }
788 }
789 }
790
791 if ( have_river_connection)
792 {
793 if ( have_water_table)
794 {
795 for (size_t sbl = 0; sbl < sb_.surfacebulk_layer_cnt(); ++sbl)
796 {
797 DISSOLUTION_ATMOSPHERE( MeTrX_get_atm_eq_liq( o2_atm_eq_liq, h_wl), sb_.o2_sbl[sbl], subdaily_o2_water[subdaily_time_step_]);
798 DISSOLUTION_ATMOSPHERE( MeTrX_get_atm_eq_liq( ch4_atm_eq_liq, h_wl), sb_.ch4_sbl[sbl], subdaily_ch4_water[subdaily_time_step_]);
799 DISSOLUTION_ATMOSPHERE( MeTrX_get_atm_eq_liq( co2_atm_eq_liq, h_wl), sb_.co2_sbl[sbl], subdaily_co2_water[subdaily_time_step_]);
800 DISSOLUTION_ATMOSPHERE( MeTrX_get_atm_eq_liq( nh3_atm_eq_liq, h_wl), sb_.nh3_sbl[sbl], subdaily_nh3_water[subdaily_time_step_]);
801 DISSOLUTION_ATMOSPHERE( MeTrX_get_atm_eq_liq( no_atm_eq_liq, h_wl), sb_.no_sbl[sbl], subdaily_no_water[subdaily_time_step_]);
802 DISSOLUTION_ATMOSPHERE( MeTrX_get_atm_eq_liq( n2o_atm_eq_liq, h_wl), sb_.n2o_sbl[sbl], subdaily_n2o_water[subdaily_time_step_]);
803 if ( have_radon_diffusion)
804 {
805 DISSOLUTION_ATMOSPHERE( MeTrX_get_atm_eq_liq( radon_atm_eq_liq, h_wl) * cbm::RGAS * mc_.ts_airtemperature, sb_.radon_sbl[sbl], subdaily_radon_water[subdaily_time_step_]);
806 }
807 }
808 }
809 }
810 }
811}

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_iron_oxidation()

void ldndc::SoilChemistryMeTrX::MeTrX_iron_oxidation ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_iron_reduction()

void ldndc::SoilChemistryMeTrX::MeTrX_iron_reduction ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_leaching()

void ldndc::SoilChemistryMeTrX::MeTrX_leaching ( )
private

Downwards transport of solutes, litter and humus with percolation water.

Parameters
[in]None
[out]None
Returns
void
26{
27 /*************************/
28 /* Water table transport */
29 /*************************/
30
31 if ( have_water_table &&
32 cbm::flt_greater_zero( infiltration))
33 {
34 ldndc_kassert( h_wl > 0.0);
35
36 accumulated_n_nh4_infiltration_leach_sl[0] -= nh4_an_sl[0] + sc_.coated_nh4_sl[0];
37 accumulated_n_nh3_infiltration_leach_sl[0] -= sc_.nh3_liq_sl[0];
38 accumulated_n_no_infiltration_leach_sl[0] -= an_no_liq_sl[0];
39 accumulated_n_n2o_infiltration_leach_sl[0] -= an_n2o_liq_sl[0];
40 accumulated_n_urea_infiltration_leach_sl[0] -= sc_.urea_sl[0];
41 accumulated_n_no3_infiltration_leach_sl[0] -= no3_an_sl[0];
42 accumulated_n_don_infiltration_leach_sl[0] -= don_an_sl[0];
43
44 double const leach_fact_sbl( cbm::bound_max( infiltration / h_wl, 0.99));
45 LEACH_DOWN( sb_.ch4_sbl[0], ch4_liq_sl[0], leach_fact_sbl);
46 LEACH_DOWN( sb_.o2_sbl[0], o2_liq_sl[0], leach_fact_sbl);
47 LEACH_DOWN( sb_.nh4_sbl[0], nh4_an_sl[0], leach_fact_sbl);
48 LEACH_DOWN( sb_.coated_nh4_sbl[0], sc_.coated_nh4_sl[0], leach_fact_sbl);
49 LEACH_DOWN( sb_.nh3_sbl[0], sc_.nh3_liq_sl[0], leach_fact_sbl);
50 LEACH_DOWN( sb_.no_sbl[0], an_no_liq_sl[0], leach_fact_sbl);
51 LEACH_DOWN( sb_.n2o_sbl[0], an_n2o_liq_sl[0], leach_fact_sbl);
52 LEACH_DOWN( sb_.urea_sbl[0], sc_.urea_sl[0], leach_fact_sbl);
53 LEACH_DOWN( sb_.no3_sbl[0], no3_an_sl[0], leach_fact_sbl);
54 LEACH_DOWN( sb_.don_sbl[0], don_an_sl[0], leach_fact_sbl);
55 LEACH_DOWN( sb_.doc_sbl[0], sc_.doc_sl[0], leach_fact_sbl);
56 LEACH_DOWN( sb_.co2_sbl[0], co2_liq_sl[0], leach_fact_sbl);
57 LEACH_DOWN( sb_.so4_sbl[0], sc_.so4_sl[0], leach_fact_sbl);
58 LEACH_DOWN( sb_.ni_sbl[0], sc_.ni_sl[0], leach_fact_sbl);
59 LEACH_DOWN( sb_.ui_sbl[0], sc_.ui_sl[0], leach_fact_sbl);
60 if ( have_radon_diffusion)
61 {
62 LEACH_DOWN( sb_.radon_sbl[0], radon_liq_sl[0], leach_fact_sbl);
63 }
64
65 accumulated_n_nh4_infiltration_leach_sl[0] += nh4_an_sl[0] + sc_.coated_nh4_sl[0];
66 accumulated_n_nh3_infiltration_leach_sl[0] += sc_.nh3_liq_sl[0];
67 accumulated_n_no_infiltration_leach_sl[0] += an_no_liq_sl[0];
68 accumulated_n_n2o_infiltration_leach_sl[0] += an_n2o_liq_sl[0];
69 accumulated_n_urea_infiltration_leach_sl[0] += sc_.urea_sl[0];
70 accumulated_n_no3_infiltration_leach_sl[0] += no3_an_sl[0];
71 accumulated_n_don_infiltration_leach_sl[0] += don_an_sl[0];
72
73 for (size_t sbl = 1; sbl < sb_.surfacebulk_layer_cnt(); ++sbl)
74 {
75 size_t const sbl_plus( sbl - 1);
76 LEACH_DOWN( sb_.ch4_sbl[sbl], sb_.ch4_sbl[sbl_plus], leach_fact_sbl);
77 LEACH_DOWN( sb_.o2_sbl[sbl], sb_.o2_sbl[sbl_plus], leach_fact_sbl);
78 LEACH_DOWN( sb_.nh4_sbl[sbl], sb_.nh4_sbl[sbl_plus], leach_fact_sbl);
79 LEACH_DOWN( sb_.coated_nh4_sbl[sbl], sb_.coated_nh4_sbl[sbl_plus], leach_fact_sbl);
80 LEACH_DOWN( sb_.nh3_sbl[sbl], sb_.nh3_sbl[sbl_plus], leach_fact_sbl);
81 LEACH_DOWN( sb_.no_sbl[sbl], sb_.no_sbl[sbl_plus], leach_fact_sbl);
82 LEACH_DOWN( sb_.n2o_sbl[sbl], sb_.n2o_sbl[sbl_plus], leach_fact_sbl);
83 LEACH_DOWN( sb_.urea_sbl[sbl], sb_.urea_sbl[sbl_plus], leach_fact_sbl);
84 LEACH_DOWN( sb_.no3_sbl[sbl], sb_.no3_sbl[sbl_plus], leach_fact_sbl);
85 LEACH_DOWN( sb_.don_sbl[sbl], sb_.don_sbl[sbl_plus], leach_fact_sbl);
86 LEACH_DOWN( sb_.doc_sbl[sbl], sb_.doc_sbl[sbl_plus], leach_fact_sbl);
87 LEACH_DOWN( sb_.co2_sbl[sbl], sb_.co2_sbl[sbl_plus], leach_fact_sbl);
88 LEACH_DOWN( sb_.so4_sbl[sbl], sb_.so4_sbl[sbl_plus], leach_fact_sbl);
89 LEACH_DOWN( sb_.ni_sbl[sbl], sb_.ni_sbl[sbl_plus], leach_fact_sbl);
90 if ( have_radon_diffusion)
91 {
92 LEACH_DOWN( sb_.radon_sbl[sbl], sb_.radon_sbl[sbl_plus], leach_fact_sbl);
93 }
94 }
95 }
96
97 /************************/
98 /* Soil water transport */
99 /************************/
100
101 if ( cbm::flt_greater_zero( waterflux_sl[0]) &&
102 cbm::flt_greater_zero( v_water_sl[0]))
103 {
104 size_t const sl( 0);
105 size_t const sl_plus( 1);
106
107 double const leach_fact( cbm::bound_min( 0.0, waterflux_sl[sl] / v_water_sl[sl]));
108
109 double const leach_fact_nh4( cbm::bound_max( leach_fact * sipar_.RETNH4(), 0.9999));
110 double const leach_fact_no3( cbm::bound_max( leach_fact * sipar_.RETNO3(), 0.9999));
111 double const leach_fact_doc( cbm::bound_max( leach_fact * sipar_.RETDOC(), 0.9999));
112 double const leach_fact_mic( cbm::bound_max( leach_fact * sipar_.METRX_RET_MICROBES(), 0.9999));
113 double const leach_fact_lit( cbm::bound_max( leach_fact * sipar_.METRX_RET_LITTER(), 0.9999));
114 double const leach_fact_hum( cbm::bound_max( leach_fact * sipar_.METRX_RET_HUMUS(), 0.9999));
115 double const leach_fact_dissolved_gases( cbm::bound_max( leach_fact, 0.9999));
116
117 if ( spinup_.spinup_stage( this->lclock()))
118 {
119 spinup_.loose_lit_1[sl] += leach_fact_lit;
120 spinup_.loose_lit_2[sl] += leach_fact_lit;
121 spinup_.loose_lit_3[sl] += leach_fact_lit;
122
123 spinup_.loose_aorg[sl] += leach_fact_mic;
124
125 spinup_.decompose_hum_1[sl] += leach_fact_hum;
126 spinup_.decompose_hum_2[sl] += leach_fact_hum;
127 spinup_.decompose_hum_3[sl] += leach_fact_hum;
128
129 spinup_.c_to_lit_1[sl_plus] += sc_.C_lit1_sl[sl] * leach_fact_lit;
130 spinup_.c_to_lit_2[sl_plus] += sc_.C_lit2_sl[sl] * leach_fact_lit;
131 spinup_.c_to_lit_3[sl_plus] += sc_.C_lit3_sl[sl] * leach_fact_lit;
132
133 spinup_.c_to_aorg[sl_plus] += sc_.C_aorg_sl[sl] * leach_fact_mic;
134
135 spinup_.c_to_humus_1_sl[sl_plus] += c_humus_1_sl[sl] * leach_fact_hum;
136 spinup_.c_to_humus_2_sl[sl_plus] += c_humus_2_sl[sl] * leach_fact_hum;
137 spinup_.c_to_humus_3_sl[sl_plus] += c_humus_3_sl[sl] * leach_fact_hum;
138 }
139
140 accumulated_n_aorg_leaching_sl[sl] += sc_.N_aorg_sl[sl] * leach_fact_mic;
141 LEACH_DOWN( sc_.C_aorg_sl[sl], sc_.C_aorg_sl[sl_plus], leach_fact_mic);
142 LEACH_DOWN( sc_.N_aorg_sl[sl], sc_.N_aorg_sl[sl_plus], leach_fact_mic);
143
144 transport_.leach_down_epsilon( sc_.C_micro1_sl[sl], sc_.C_micro1_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_c_decay_max( sc_.C_micro1_sl[sl]));
145 transport_.leach_down_epsilon( sc_.C_micro2_sl[sl], sc_.C_micro2_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_c_decay_max( sc_.C_micro2_sl[sl]));
146 transport_.leach_down_epsilon( sc_.C_micro3_sl[sl], sc_.C_micro3_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_c_decay_max( sc_.C_micro3_sl[sl]));
147
148 if( n_micro_1_sl[sl] > MeTrX_get_micro_n_decay_max( n_micro_1_sl[sl]) )
149 {
150 accumulated_n_micro_leaching_sl[sl] += ( n_micro_1_sl[sl] - MeTrX_get_micro_n_decay_max( n_micro_1_sl[sl]) ) * leach_fact_mic;
151 }
152 if( n_micro_2_sl[sl] > MeTrX_get_micro_n_decay_max( n_micro_2_sl[sl]) )
153 {
154 accumulated_n_micro_leaching_sl[sl] += ( n_micro_2_sl[sl] - MeTrX_get_micro_n_decay_max( n_micro_2_sl[sl]) ) * leach_fact_mic;
155 }
156 if( n_micro_3_sl[sl] > MeTrX_get_micro_n_decay_max( n_micro_3_sl[sl]) )
157 {
158 accumulated_n_micro_leaching_sl[sl] += ( n_micro_3_sl[sl] - MeTrX_get_micro_n_decay_max( n_micro_3_sl[sl]) ) * leach_fact_mic;
159 }
160 transport_.leach_down_epsilon( n_micro_1_sl[sl], n_micro_1_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_n_decay_max( n_micro_1_sl[sl]));
161 transport_.leach_down_epsilon( n_micro_2_sl[sl], n_micro_2_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_n_decay_max( n_micro_2_sl[sl]));
162 transport_.leach_down_epsilon( n_micro_3_sl[sl], n_micro_3_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_n_decay_max( n_micro_3_sl[sl]));
163
164 LEACH_DOWN( sc_.C_lit1_sl[sl], sc_.C_lit1_sl[sl_plus], leach_fact_lit);
165 LEACH_DOWN( sc_.C_lit2_sl[sl], sc_.C_lit2_sl[sl_plus], leach_fact_lit);
166 LEACH_DOWN( sc_.C_lit3_sl[sl], sc_.C_lit3_sl[sl_plus], leach_fact_lit);
167
168 accumulated_n_litter_leaching_sl[sl] += (sc_.N_lit1_sl[sl] + sc_.N_lit2_sl[sl] + sc_.N_lit3_sl[sl]) * leach_fact_lit;
169 LEACH_DOWN( sc_.N_lit1_sl[sl], sc_.N_lit1_sl[sl_plus], leach_fact_lit);
170 LEACH_DOWN( sc_.N_lit2_sl[sl], sc_.N_lit2_sl[sl_plus], leach_fact_lit);
171 LEACH_DOWN( sc_.N_lit3_sl[sl], sc_.N_lit3_sl[sl_plus], leach_fact_lit);
172
173 LEACH_DOWN( c_humus_1_sl[sl], c_humus_1_sl[sl_plus], leach_fact_hum);
174 LEACH_DOWN( c_humus_2_sl[sl], c_humus_2_sl[sl_plus], leach_fact_hum);
175 LEACH_DOWN( c_humus_3_sl[sl], c_humus_3_sl[sl_plus], leach_fact_hum);
176
177 accumulated_n_humus_1_leaching_sl[sl] += n_humus_1_sl[sl] * leach_fact_hum;
178 accumulated_n_humus_2_leaching_sl[sl] += n_humus_2_sl[sl] * leach_fact_hum;
179 accumulated_n_humus_3_leaching_sl[sl] += n_humus_3_sl[sl] * leach_fact_hum;
180 LEACH_DOWN( n_humus_1_sl[sl], n_humus_1_sl[sl_plus], leach_fact_hum);
181 LEACH_DOWN( n_humus_2_sl[sl], n_humus_2_sl[sl_plus], leach_fact_hum);
182 LEACH_DOWN( n_humus_3_sl[sl], n_humus_3_sl[sl_plus], leach_fact_hum);
183
184 accumulated_n_nh4_leaching_sl[sl] += (nh4_ae_sl[sl] + nh4_an_sl[sl] + sc_.coated_nh4_sl[sl]) * leach_fact_nh4;
185 accumulated_n_nh3_leaching_sl[sl] += sc_.nh3_liq_sl[sl] * leach_fact_doc;
186 accumulated_n_urea_leaching_sl[sl] += sc_.urea_sl[sl] * leach_fact_doc;
187 LEACH_DOWN( nh4_ae_sl[sl], nh4_ae_sl[sl_plus], leach_fact_nh4);
188 LEACH_DOWN( nh4_an_sl[sl], nh4_an_sl[sl_plus], leach_fact_nh4);
189 LEACH_DOWN( sc_.coated_nh4_sl[sl], sc_.coated_nh4_sl[sl_plus], leach_fact_nh4);
190 LEACH_DOWN( sc_.nh3_liq_sl[sl], sc_.nh3_liq_sl[sl_plus], leach_fact_doc);
191 LEACH_DOWN( sc_.urea_sl[sl], sc_.urea_sl[sl_plus], leach_fact_doc);
192
193 sc_.accumulated_n_no3_leaching_sl[sl] += (no3_ae_sl[sl] + no3_an_sl[sl]) * leach_fact_no3;
194 LEACH_DOWN( no3_ae_sl[sl], no3_ae_sl[sl_plus], leach_fact_no3);
195 LEACH_DOWN( no3_an_sl[sl], no3_an_sl[sl_plus], leach_fact_no3);
196
197 accumulated_n_don_leaching_sl[sl] += (don_ae_sl[sl] + don_an_sl[sl]) * leach_fact_doc;
198 LEACH_DOWN( don_ae_sl[sl], don_ae_sl[sl_plus], leach_fact_doc);
199 LEACH_DOWN( don_an_sl[sl], don_an_sl[sl_plus], leach_fact_doc);
200 LEACH_DOWN( sc_.doc_sl[sl], sc_.doc_sl[sl_plus], leach_fact_doc);
201 LEACH_DOWN( sc_.an_doc_sl[sl], sc_.an_doc_sl[sl_plus], leach_fact_doc);
202 LEACH_DOWN( ae_acetate_sl[sl], ae_acetate_sl[sl_plus], leach_fact_doc);
203 LEACH_DOWN( an_acetate_sl[sl], an_acetate_sl[sl_plus], leach_fact_doc);
204
205 accumulated_n_no_leaching_sl[sl] += (no_liq_sl[sl]+an_no_liq_sl[sl]) * leach_fact_dissolved_gases;
206 accumulated_n_n2o_leaching_sl[sl] += (n2o_liq_sl[sl]+an_n2o_liq_sl[sl]) * leach_fact_dissolved_gases;
207 LEACH_DOWN( no_liq_sl[sl], no_liq_sl[sl_plus], leach_fact_dissolved_gases);
208 LEACH_DOWN( an_no_liq_sl[sl], an_no_liq_sl[sl_plus], leach_fact_dissolved_gases);
209 LEACH_DOWN( n2o_liq_sl[sl], n2o_liq_sl[sl_plus], leach_fact_dissolved_gases);
210 LEACH_DOWN( an_n2o_liq_sl[sl], an_n2o_liq_sl[sl_plus], leach_fact_dissolved_gases);
211
212 LEACH_DOWN( ch4_liq_sl[sl], ch4_liq_sl[sl_plus], leach_fact_dissolved_gases);
213 LEACH_DOWN( co2_liq_sl[sl], co2_liq_sl[sl_plus], leach_fact_dissolved_gases);
214 LEACH_DOWN( o2_liq_sl[sl], o2_liq_sl[sl_plus], leach_fact_dissolved_gases);
215
216 LEACH_DOWN( sc_.so4_sl[sl], sc_.so4_sl[sl_plus], leach_fact_no3);
217 LEACH_DOWN( sc_.ni_sl[sl], sc_.ni_sl[sl_plus], leach_fact_doc);
218 LEACH_DOWN( sc_.ui_sl[sl], sc_.ui_sl[sl_plus], leach_fact_doc);
219
220 if ( have_radon_diffusion)
221 {
222 LEACH_DOWN( radon_liq_sl[sl], radon_liq_sl[sl_plus], leach_fact_dissolved_gases);
223 }
224 }
225
226 for( size_t sl = 1; sl < sl_.soil_layer_cnt()-1; ++sl)
227 {
228 if ( cbm::flt_equal_zero( v_water_sl[sl]) ||
229 cbm::flt_equal_zero( waterflux_sl[sl]))
230 {
231 continue;
232 }
233
234 size_t sl_plus( sl + 1);
235 if ( cbm::flt_less( waterflux_sl[sl], 0.0))
236 {
237 sl_plus = sl - 1;
238 }
239
240 //take absolute value (negative fluxes are handled by sl_plus
241 double const leach_fact( std::abs( waterflux_sl[sl] / v_water_sl[sl]));
242
243 double const leach_fact_nh4( cbm::bound_max( leach_fact * sipar_.RETNH4(), 0.9999));
244 double const leach_fact_no3( cbm::bound_max( leach_fact * sipar_.RETNO3(), 0.9999));
245 double const leach_fact_doc( cbm::bound_max( leach_fact * sipar_.RETDOC(), 0.9999));
246 double const leach_fact_mic( cbm::bound_max( leach_fact * sipar_.METRX_RET_MICROBES(), 0.9999));
247 double const leach_fact_lit( cbm::bound_max( leach_fact * sipar_.METRX_RET_LITTER(), 0.9999));
248 double const leach_fact_hum( cbm::bound_max( leach_fact * sipar_.METRX_RET_HUMUS(), 0.9999));
249 double const leach_fact_dissolved_gases( cbm::bound_max( leach_fact, 0.9999));
250
251 if ( spinup_.spinup_stage( this->lclock()))
252 {
253 spinup_.loose_lit_1[sl] += leach_fact_lit;
254 spinup_.loose_lit_2[sl] += leach_fact_lit;
255 spinup_.loose_lit_3[sl] += leach_fact_lit;
256
257 spinup_.loose_aorg[sl] += leach_fact_mic;
258
259 spinup_.decompose_hum_1[sl] += leach_fact_hum;
260 spinup_.decompose_hum_2[sl] += leach_fact_hum;
261 spinup_.decompose_hum_3[sl] += leach_fact_hum;
262
263 spinup_.c_to_lit_1[sl_plus] += sc_.C_lit1_sl[sl] * leach_fact_lit;
264 spinup_.c_to_lit_2[sl_plus] += sc_.C_lit2_sl[sl] * leach_fact_lit;
265 spinup_.c_to_lit_3[sl_plus] += sc_.C_lit3_sl[sl] * leach_fact_lit;
266
267 spinup_.c_to_aorg[sl_plus] += sc_.C_aorg_sl[sl] * leach_fact_mic;
268
269 spinup_.c_to_humus_1_sl[sl_plus] += c_humus_1_sl[sl] * leach_fact_hum;
270 spinup_.c_to_humus_2_sl[sl_plus] += c_humus_2_sl[sl] * leach_fact_hum;
271 spinup_.c_to_humus_3_sl[sl_plus] += c_humus_3_sl[sl] * leach_fact_hum;
272 }
273
274 accumulated_n_aorg_leaching_sl[sl] += sc_.N_aorg_sl[sl] * leach_fact_mic;
275 LEACH_DOWN( sc_.C_aorg_sl[sl], sc_.C_aorg_sl[sl_plus], leach_fact_mic);
276 LEACH_DOWN( sc_.N_aorg_sl[sl], sc_.N_aorg_sl[sl_plus], leach_fact_mic);
277
278 LEACH_DOWN_EPSILON( sc_.C_micro1_sl[sl], sc_.C_micro1_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_c_decay_max( sc_.C_micro1_sl[sl]));
279 LEACH_DOWN_EPSILON( sc_.C_micro2_sl[sl], sc_.C_micro2_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_c_decay_max( sc_.C_micro2_sl[sl]));
280 LEACH_DOWN_EPSILON( sc_.C_micro3_sl[sl], sc_.C_micro3_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_c_decay_max( sc_.C_micro3_sl[sl]));
281
282 if( n_micro_1_sl[sl] > MeTrX_get_micro_n_decay_max( n_micro_1_sl[sl]) )
283 {
284 accumulated_n_micro_leaching_sl[sl] += ( n_micro_1_sl[sl] - MeTrX_get_micro_n_decay_max( n_micro_1_sl[sl]) ) * leach_fact_mic;
285 }
286 if( n_micro_2_sl[sl] > MeTrX_get_micro_n_decay_max( n_micro_2_sl[sl]) )
287 {
288 accumulated_n_micro_leaching_sl[sl] += ( n_micro_2_sl[sl] - MeTrX_get_micro_n_decay_max( n_micro_2_sl[sl]) ) * leach_fact_mic;
289 }
290 if( n_micro_3_sl[sl] > MeTrX_get_micro_n_decay_max( n_micro_3_sl[sl]) )
291 {
292 accumulated_n_micro_leaching_sl[sl] += ( n_micro_3_sl[sl] - MeTrX_get_micro_n_decay_max( n_micro_3_sl[sl]) ) * leach_fact_mic;
293 }
294 LEACH_DOWN_EPSILON( n_micro_1_sl[sl], n_micro_1_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_n_decay_max( n_micro_1_sl[sl]));
295 LEACH_DOWN_EPSILON( n_micro_2_sl[sl], n_micro_2_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_n_decay_max( n_micro_2_sl[sl]));
296 LEACH_DOWN_EPSILON( n_micro_3_sl[sl], n_micro_3_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_n_decay_max( n_micro_3_sl[sl]));
297
298 LEACH_DOWN( sc_.C_lit1_sl[sl], sc_.C_lit1_sl[sl_plus], leach_fact_lit);
299 LEACH_DOWN( sc_.C_lit2_sl[sl], sc_.C_lit2_sl[sl_plus], leach_fact_lit);
300 LEACH_DOWN( sc_.C_lit3_sl[sl], sc_.C_lit3_sl[sl_plus], leach_fact_lit);
301
302 accumulated_n_litter_leaching_sl[sl] += (sc_.N_lit1_sl[sl]+sc_.N_lit2_sl[sl]+sc_.N_lit3_sl[sl]) * leach_fact_lit;
303 LEACH_DOWN( sc_.N_lit1_sl[sl], sc_.N_lit1_sl[sl_plus], leach_fact_lit);
304 LEACH_DOWN( sc_.N_lit2_sl[sl], sc_.N_lit2_sl[sl_plus], leach_fact_lit);
305 LEACH_DOWN( sc_.N_lit3_sl[sl], sc_.N_lit3_sl[sl_plus], leach_fact_lit);
306
307 LEACH_DOWN( c_humus_1_sl[sl], c_humus_1_sl[sl_plus], leach_fact_hum);
308 LEACH_DOWN( c_humus_2_sl[sl], c_humus_2_sl[sl_plus], leach_fact_hum);
309 LEACH_DOWN( c_humus_3_sl[sl], c_humus_3_sl[sl_plus], leach_fact_hum);
310
311 accumulated_n_humus_1_leaching_sl[sl] += n_humus_1_sl[sl] * leach_fact_hum;
312 accumulated_n_humus_2_leaching_sl[sl] += n_humus_2_sl[sl] * leach_fact_hum;
313 accumulated_n_humus_3_leaching_sl[sl] += n_humus_3_sl[sl] * leach_fact_hum;
314 LEACH_DOWN( n_humus_1_sl[sl], n_humus_1_sl[sl_plus], leach_fact_hum);
315 LEACH_DOWN( n_humus_2_sl[sl], n_humus_2_sl[sl_plus], leach_fact_hum);
316 LEACH_DOWN( n_humus_3_sl[sl], n_humus_3_sl[sl_plus], leach_fact_hum);
317
318 accumulated_n_nh4_leaching_sl[sl] += (nh4_ae_sl[sl] + nh4_an_sl[sl] + sc_.coated_nh4_sl[sl]) * leach_fact_nh4;
319 accumulated_n_nh3_leaching_sl[sl] += sc_.nh3_liq_sl[sl] * leach_fact_doc;
320 accumulated_n_urea_leaching_sl[sl] += sc_.urea_sl[sl] * leach_fact_doc;
321 LEACH_DOWN( nh4_ae_sl[sl], nh4_ae_sl[sl_plus], leach_fact_nh4);
322 LEACH_DOWN( nh4_an_sl[sl], nh4_an_sl[sl_plus], leach_fact_nh4);
323 LEACH_DOWN( sc_.coated_nh4_sl[sl], sc_.coated_nh4_sl[sl_plus], leach_fact_nh4);
324 LEACH_DOWN( sc_.nh3_liq_sl[sl], sc_.nh3_liq_sl[sl_plus], leach_fact_doc);
325 LEACH_DOWN( sc_.urea_sl[sl], sc_.urea_sl[sl_plus], leach_fact_doc);
326
327 sc_.accumulated_n_no3_leaching_sl[sl] += (no3_ae_sl[sl]+no3_an_sl[sl]) * leach_fact_no3;
328 LEACH_DOWN( no3_ae_sl[sl], no3_ae_sl[sl_plus], leach_fact_no3);
329 LEACH_DOWN( no3_an_sl[sl], no3_an_sl[sl_plus], leach_fact_no3);
330
331 accumulated_n_don_leaching_sl[sl] += (don_ae_sl[sl] + don_an_sl[sl]) * leach_fact_doc;
332 LEACH_DOWN( don_ae_sl[sl], don_ae_sl[sl_plus], leach_fact_doc);
333 LEACH_DOWN( don_an_sl[sl], don_an_sl[sl_plus], leach_fact_doc);
334 LEACH_DOWN( sc_.doc_sl[sl], sc_.doc_sl[sl_plus], leach_fact_doc);
335 LEACH_DOWN( sc_.an_doc_sl[sl], sc_.an_doc_sl[sl_plus], leach_fact_doc);
336 LEACH_DOWN( ae_acetate_sl[sl], ae_acetate_sl[sl_plus], leach_fact_doc);
337 LEACH_DOWN( an_acetate_sl[sl], an_acetate_sl[sl_plus], leach_fact_doc);
338
339 accumulated_n_no_leaching_sl[sl] += (no_liq_sl[sl]+an_no_liq_sl[sl]) * leach_fact_dissolved_gases;
340 accumulated_n_n2o_leaching_sl[sl] += (n2o_liq_sl[sl]+an_n2o_liq_sl[sl]) * leach_fact_dissolved_gases;
341 LEACH_DOWN( no_liq_sl[sl], no_liq_sl[sl_plus], leach_fact_dissolved_gases);
342 LEACH_DOWN( an_no_liq_sl[sl], an_no_liq_sl[sl_plus], leach_fact_dissolved_gases);
343 LEACH_DOWN( n2o_liq_sl[sl], n2o_liq_sl[sl_plus], leach_fact_dissolved_gases);
344 LEACH_DOWN( an_n2o_liq_sl[sl], an_n2o_liq_sl[sl_plus], leach_fact_dissolved_gases);
345
346 LEACH_DOWN( ch4_liq_sl[sl], ch4_liq_sl[sl_plus], leach_fact_dissolved_gases);
347 LEACH_DOWN( co2_liq_sl[sl], co2_liq_sl[sl_plus], leach_fact_dissolved_gases);
348 LEACH_DOWN( o2_liq_sl[sl], o2_liq_sl[sl_plus], leach_fact_dissolved_gases);
349
350 LEACH_DOWN( sc_.so4_sl[sl], sc_.so4_sl[sl_plus], leach_fact_no3);
351 LEACH_DOWN( sc_.ni_sl[sl], sc_.ni_sl[sl_plus], leach_fact_doc);
352 LEACH_DOWN( sc_.ui_sl[sl], sc_.ui_sl[sl_plus], leach_fact_doc);
353
354 if ( have_radon_diffusion)
355 {
356 LEACH_DOWN( radon_liq_sl[sl], radon_liq_sl[sl_plus], leach_fact_dissolved_gases);
357 }
358 }
359
360 size_t sl( sl_.soil_layer_cnt()-1);
361
362 if ( cbm::flt_greater_zero( v_water_sl[sl]))
363 {
364 if ( cbm::flt_greater_zero( waterflux_sl[sl]))
365 {
366 double dummy_out( 0.0); //dummy for substances that are not balanced (no accumulated leaching variable exists)
367
368 double const leach_fact( waterflux_sl[sl] / v_water_sl[sl]);
369
370 double const leach_fact_nh4( cbm::bound_max( leach_fact * sipar_.RETNH4(), 0.9999));
371 double const leach_fact_no3( cbm::bound_max( leach_fact * sipar_.RETNO3(), 0.9999));
372 double const leach_fact_doc( cbm::bound_max( leach_fact * sipar_.RETDOC(), 0.9999));
373 double const leach_fact_mic( cbm::bound_max( leach_fact * sipar_.METRX_RET_MICROBES(), 0.9999));
374 double const leach_fact_lit( cbm::bound_max( leach_fact * sipar_.METRX_RET_LITTER(), 0.9999));
375 double const leach_fact_hum( cbm::bound_max( leach_fact * sipar_.METRX_RET_HUMUS(), 0.9999));
376 double const leach_fact_dissolved_gases( cbm::bound_max( leach_fact, 0.9999));
377
378 if ( spinup_.spinup_stage( this->lclock()))
379 {
380 spinup_.loose_lit_1[sl] += leach_fact_lit;
381 spinup_.loose_lit_2[sl] += leach_fact_lit;
382 spinup_.loose_lit_3[sl] += leach_fact_lit;
383
384 spinup_.loose_aorg[sl] += leach_fact_mic;
385
386 spinup_.decompose_hum_1[sl] += leach_fact_hum;
387 spinup_.decompose_hum_2[sl] += leach_fact_hum;
388 spinup_.decompose_hum_3[sl] += leach_fact_hum;
389 }
390
391 accumulated_n_aorg_leaching_sl[sl] += sc_.N_aorg_sl[sl] * leach_fact_mic;
392 LEACH_DOWN( sc_.C_aorg_sl[sl], sc_.accumulated_doc_leach, leach_fact_mic);
393 LEACH_DOWN( sc_.N_aorg_sl[sl], sc_.accumulated_don_leach, leach_fact_mic);
394
395 LEACH_DOWN_EPSILON( sc_.C_micro1_sl[sl], sc_.accumulated_doc_leach, leach_fact_mic, MeTrX_get_micro_c_decay_max( sc_.C_micro1_sl[sl]));
396 LEACH_DOWN_EPSILON( sc_.C_micro2_sl[sl], sc_.accumulated_doc_leach, leach_fact_mic, MeTrX_get_micro_c_decay_max( sc_.C_micro2_sl[sl]));
397 LEACH_DOWN_EPSILON( sc_.C_micro3_sl[sl], sc_.accumulated_doc_leach, leach_fact_mic, MeTrX_get_micro_c_decay_max( sc_.C_micro3_sl[sl]));
398
399 if( n_micro_1_sl[sl] > MeTrX_get_micro_n_decay_max( n_micro_1_sl[sl]) )
400 {
401 accumulated_n_micro_leaching_sl[sl] += ( n_micro_1_sl[sl] - MeTrX_get_micro_n_decay_max( n_micro_1_sl[sl]) ) * leach_fact_mic;
402 }
403 if( n_micro_2_sl[sl] > MeTrX_get_micro_n_decay_max( n_micro_2_sl[sl]) )
404 {
405 accumulated_n_micro_leaching_sl[sl] += ( n_micro_2_sl[sl] - MeTrX_get_micro_n_decay_max( n_micro_2_sl[sl]) ) * leach_fact_mic;
406 }
407 if( n_micro_3_sl[sl] > MeTrX_get_micro_n_decay_max( n_micro_3_sl[sl]) )
408 {
409 accumulated_n_micro_leaching_sl[sl] += ( n_micro_3_sl[sl] - MeTrX_get_micro_n_decay_max( n_micro_3_sl[sl]) ) * leach_fact_mic;
410 }
411 LEACH_DOWN_EPSILON( n_micro_1_sl[sl], sc_.accumulated_don_leach, leach_fact_mic, MeTrX_get_micro_n_decay_max( n_micro_1_sl[sl]));
412 LEACH_DOWN_EPSILON( n_micro_2_sl[sl], sc_.accumulated_don_leach, leach_fact_mic, MeTrX_get_micro_n_decay_max( n_micro_2_sl[sl]));
413 LEACH_DOWN_EPSILON( n_micro_3_sl[sl], sc_.accumulated_don_leach, leach_fact_mic, MeTrX_get_micro_n_decay_max( n_micro_3_sl[sl]));
414
415 LEACH_DOWN( sc_.C_lit1_sl[sl], sc_.accumulated_doc_leach, leach_fact_lit);
416 LEACH_DOWN( sc_.C_lit2_sl[sl], sc_.accumulated_doc_leach, leach_fact_lit);
417 LEACH_DOWN( sc_.C_lit3_sl[sl], sc_.accumulated_doc_leach, leach_fact_lit);
418
419 accumulated_n_litter_leaching_sl[sl] += (sc_.N_lit1_sl[sl]+sc_.N_lit2_sl[sl]+sc_.N_lit3_sl[sl]) * leach_fact_lit;
420 LEACH_DOWN( sc_.N_lit1_sl[sl], sc_.accumulated_don_leach, leach_fact_lit);
421 LEACH_DOWN( sc_.N_lit2_sl[sl], sc_.accumulated_don_leach, leach_fact_lit);
422 LEACH_DOWN( sc_.N_lit3_sl[sl], sc_.accumulated_don_leach, leach_fact_lit);
423
424 LEACH_DOWN( c_humus_1_sl[sl], sc_.accumulated_doc_leach, leach_fact_hum);
425 LEACH_DOWN( c_humus_2_sl[sl], sc_.accumulated_doc_leach, leach_fact_hum);
426 LEACH_DOWN( c_humus_3_sl[sl], sc_.accumulated_doc_leach, leach_fact_hum);
427
428 accumulated_n_humus_1_leaching_sl[sl] += n_humus_1_sl[sl] * leach_fact_hum;
429 accumulated_n_humus_2_leaching_sl[sl] += n_humus_2_sl[sl] * leach_fact_hum;
430 accumulated_n_humus_3_leaching_sl[sl] += n_humus_3_sl[sl] * leach_fact_hum;
431 LEACH_DOWN( n_humus_1_sl[sl], sc_.accumulated_don_leach, leach_fact_hum);
432 LEACH_DOWN( n_humus_2_sl[sl], sc_.accumulated_don_leach, leach_fact_hum);
433 LEACH_DOWN( n_humus_2_sl[sl], sc_.accumulated_don_leach, leach_fact_hum);
434
435 accumulated_n_nh4_leaching_sl[sl] += (nh4_ae_sl[sl] + nh4_an_sl[sl] + sc_.coated_nh4_sl[sl]) * leach_fact_nh4;
436 accumulated_n_nh3_leaching_sl[sl] += sc_.nh3_liq_sl[sl] * leach_fact_doc;
437 accumulated_n_urea_leaching_sl[sl] += sc_.urea_sl[sl] * leach_fact_doc;
438 LEACH_DOWN( nh4_ae_sl[sl], sc_.accumulated_nh4_leach, leach_fact_nh4);
439 LEACH_DOWN( nh4_an_sl[sl], sc_.accumulated_nh4_leach, leach_fact_nh4);
440 LEACH_DOWN( sc_.coated_nh4_sl[sl], sc_.accumulated_nh4_leach, leach_fact_nh4);
441 LEACH_DOWN( sc_.nh3_liq_sl[sl], day_leach_nh3, leach_fact_doc);
442 LEACH_DOWN( sc_.urea_sl[sl], day_leach_urea, leach_fact_doc);
443
444 sc_.accumulated_n_no3_leaching_sl[sl] += (no3_ae_sl[sl]+no3_an_sl[sl]) * leach_fact_no3;
445 LEACH_DOWN( no3_ae_sl[sl], sc_.accumulated_no3_leach, leach_fact_no3);
446 LEACH_DOWN( no3_an_sl[sl], sc_.accumulated_no3_leach, leach_fact_no3);
447
448 accumulated_n_don_leaching_sl[sl] += (don_ae_sl[sl] + don_an_sl[sl]) * leach_fact_doc;
449 LEACH_DOWN( don_ae_sl[sl], sc_.accumulated_don_leach, leach_fact_doc);
450 LEACH_DOWN( don_an_sl[sl], sc_.accumulated_don_leach, leach_fact_doc);
451 LEACH_DOWN( sc_.doc_sl[sl], sc_.accumulated_doc_leach, leach_fact_doc);
452 LEACH_DOWN( sc_.an_doc_sl[sl], sc_.accumulated_doc_leach, leach_fact_doc);
453 LEACH_DOWN( ae_acetate_sl[sl], sc_.accumulated_doc_leach, leach_fact_doc);
454 LEACH_DOWN( an_acetate_sl[sl], sc_.accumulated_doc_leach, leach_fact_doc);
455
456 accumulated_n_no_leaching_sl[sl] += (no_liq_sl[sl]+an_no_liq_sl[sl]) * leach_fact_dissolved_gases;
457 accumulated_n_n2o_leaching_sl[sl] += (n2o_liq_sl[sl]+an_n2o_liq_sl[sl]) * leach_fact_dissolved_gases;
458 LEACH_DOWN( no_liq_sl[sl], day_leach_no, leach_fact_dissolved_gases);
459 LEACH_DOWN( an_no_liq_sl[sl], day_leach_no, leach_fact_dissolved_gases);
460 LEACH_DOWN( n2o_liq_sl[sl], day_leach_n2o, leach_fact_dissolved_gases);
461 LEACH_DOWN( an_n2o_liq_sl[sl], day_leach_n2o, leach_fact_dissolved_gases);
462 LEACH_DOWN( o2_liq_sl[sl], day_leach_o2, leach_fact_dissolved_gases);
463
464 LEACH_DOWN( ch4_liq_sl[sl], subdaily_ch4_leach[subdaily_time_step_], leach_fact_dissolved_gases);
465 LEACH_DOWN( co2_liq_sl[sl], subdaily_co2_leach[subdaily_time_step_], leach_fact_dissolved_gases);
466
467 LEACH_DOWN( sc_.so4_sl[sl], sc_.accumulated_so4_leach, leach_fact_no3);
468 LEACH_DOWN( sc_.ni_sl[sl], dummy_out, leach_fact_doc);
469 LEACH_DOWN( sc_.ui_sl[sl], dummy_out, leach_fact_doc);
470
471 if ( have_radon_diffusion)
472 {
473 LEACH_DOWN( radon_liq_sl[sl], day_leach_radon, leach_fact_dissolved_gases);
474 }
475 }
476 else if ( cbm::flt_less( waterflux_sl[sl], 0.0))
477 {
478 size_t sl_plus( sl - 1);
479
480 double const leach_fact( -1.0 * waterflux_sl[sl] / v_water_sl[sl]);
481
482 double const leach_fact_nh4( cbm::bound_max( leach_fact * sipar_.RETNH4(), 0.9999));
483 double const leach_fact_no3( cbm::bound_max( leach_fact * sipar_.RETNO3(), 0.9999));
484 double const leach_fact_doc( cbm::bound_max( leach_fact * sipar_.RETDOC(), 0.9999));
485 double const leach_fact_mic( cbm::bound_max( leach_fact * sipar_.METRX_RET_MICROBES(), 0.9999));
486 double const leach_fact_lit( cbm::bound_max( leach_fact * sipar_.METRX_RET_LITTER(), 0.9999));
487 double const leach_fact_hum( cbm::bound_max( leach_fact * sipar_.METRX_RET_HUMUS(), 0.9999));
488 double const leach_fact_dissolved_gases( cbm::bound_max( leach_fact, 0.9999));
489
490 if ( spinup_.spinup_stage( this->lclock()))
491 {
492 spinup_.loose_lit_1[sl] += leach_fact_lit;
493 spinup_.loose_lit_2[sl] += leach_fact_lit;
494 spinup_.loose_lit_3[sl] += leach_fact_lit;
495
496 spinup_.loose_aorg[sl] += leach_fact_mic;
497
498 spinup_.decompose_hum_1[sl] += leach_fact_hum;
499 spinup_.decompose_hum_2[sl] += leach_fact_hum;
500 spinup_.decompose_hum_3[sl] += leach_fact_hum;
501
502 spinup_.c_to_lit_1[sl_plus] += sc_.C_lit1_sl[sl] * leach_fact_lit;
503 spinup_.c_to_lit_2[sl_plus] += sc_.C_lit2_sl[sl] * leach_fact_lit;
504 spinup_.c_to_lit_3[sl_plus] += sc_.C_lit3_sl[sl] * leach_fact_lit;
505
506 spinup_.c_to_aorg[sl_plus] += sc_.C_aorg_sl[sl] * leach_fact_mic;
507
508 spinup_.c_to_humus_1_sl[sl_plus] += c_humus_1_sl[sl] * leach_fact_hum;
509 spinup_.c_to_humus_2_sl[sl_plus] += c_humus_2_sl[sl] * leach_fact_hum;
510 spinup_.c_to_humus_3_sl[sl_plus] += c_humus_3_sl[sl] * leach_fact_hum;
511 }
512
513 accumulated_n_aorg_leaching_sl[sl] += sc_.N_aorg_sl[sl] * leach_fact_mic;
514 LEACH_DOWN( sc_.C_aorg_sl[sl], sc_.C_aorg_sl[sl_plus], leach_fact_mic);
515 LEACH_DOWN( sc_.N_aorg_sl[sl], sc_.N_aorg_sl[sl_plus], leach_fact_mic);
516
517 LEACH_DOWN_EPSILON( sc_.C_micro1_sl[sl], sc_.C_micro1_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_c_decay_max( sc_.C_micro1_sl[sl]));
518 LEACH_DOWN_EPSILON( sc_.C_micro2_sl[sl], sc_.C_micro2_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_c_decay_max( sc_.C_micro2_sl[sl]));
519 LEACH_DOWN_EPSILON( sc_.C_micro3_sl[sl], sc_.C_micro3_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_c_decay_max( sc_.C_micro3_sl[sl]));
520
521 if( n_micro_1_sl[sl] > MeTrX_get_micro_n_decay_max( n_micro_1_sl[sl]) )
522 {
523 accumulated_n_micro_leaching_sl[sl] += ( n_micro_1_sl[sl] - MeTrX_get_micro_n_decay_max( n_micro_1_sl[sl]) ) * leach_fact_mic;
524 }
525 if( n_micro_2_sl[sl] > MeTrX_get_micro_n_decay_max( n_micro_2_sl[sl]) )
526 {
527 accumulated_n_micro_leaching_sl[sl] += ( n_micro_2_sl[sl] - MeTrX_get_micro_n_decay_max( n_micro_2_sl[sl]) ) * leach_fact_mic;
528 }
529 if( n_micro_3_sl[sl] > MeTrX_get_micro_n_decay_max( n_micro_3_sl[sl]) )
530 {
531 accumulated_n_micro_leaching_sl[sl] += ( n_micro_3_sl[sl] - MeTrX_get_micro_n_decay_max( n_micro_3_sl[sl]) ) * leach_fact_mic;
532 }
533 LEACH_DOWN_EPSILON( n_micro_1_sl[sl], n_micro_1_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_n_decay_max( n_micro_1_sl[sl]));
534 LEACH_DOWN_EPSILON( n_micro_2_sl[sl], n_micro_1_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_n_decay_max( n_micro_2_sl[sl]));
535 LEACH_DOWN_EPSILON( n_micro_3_sl[sl], n_micro_1_sl[sl_plus], leach_fact_mic, MeTrX_get_micro_n_decay_max( n_micro_3_sl[sl]));
536
537 LEACH_DOWN( sc_.C_lit1_sl[sl], sc_.C_lit1_sl[sl_plus], leach_fact_lit);
538 LEACH_DOWN( sc_.C_lit2_sl[sl], sc_.C_lit2_sl[sl_plus], leach_fact_lit);
539 LEACH_DOWN( sc_.C_lit3_sl[sl], sc_.C_lit3_sl[sl_plus], leach_fact_lit);
540
541 accumulated_n_litter_leaching_sl[sl] += (sc_.N_lit1_sl[sl]+sc_.N_lit2_sl[sl]+sc_.N_lit3_sl[sl]) * leach_fact_lit;
542 LEACH_DOWN( sc_.N_lit1_sl[sl], sc_.N_lit1_sl[sl_plus], leach_fact_lit);
543 LEACH_DOWN( sc_.N_lit2_sl[sl], sc_.N_lit2_sl[sl_plus], leach_fact_lit);
544 LEACH_DOWN( sc_.N_lit3_sl[sl], sc_.N_lit3_sl[sl_plus], leach_fact_lit);
545
546 LEACH_DOWN( c_humus_1_sl[sl], c_humus_1_sl[sl_plus], leach_fact_hum);
547 LEACH_DOWN( c_humus_2_sl[sl], c_humus_2_sl[sl_plus], leach_fact_hum);
548 LEACH_DOWN( c_humus_3_sl[sl], c_humus_3_sl[sl_plus], leach_fact_hum);
549
550 accumulated_n_humus_1_leaching_sl[sl] += n_humus_1_sl[sl] * leach_fact_hum;
551 accumulated_n_humus_2_leaching_sl[sl] += n_humus_2_sl[sl] * leach_fact_hum;
552 accumulated_n_humus_3_leaching_sl[sl] += n_humus_3_sl[sl] * leach_fact_hum;
553 LEACH_DOWN( n_humus_1_sl[sl], n_humus_1_sl[sl_plus], leach_fact_hum);
554 LEACH_DOWN( n_humus_2_sl[sl], n_humus_2_sl[sl_plus], leach_fact_hum);
555 LEACH_DOWN( n_humus_2_sl[sl], n_humus_3_sl[sl_plus], leach_fact_hum);
556
557 accumulated_n_nh4_leaching_sl[sl] += (nh4_ae_sl[sl] + nh4_an_sl[sl] + sc_.coated_nh4_sl[sl]) * leach_fact_nh4;
558 accumulated_n_nh3_leaching_sl[sl] += sc_.nh3_liq_sl[sl] * leach_fact_doc;
559 accumulated_n_urea_leaching_sl[sl] += sc_.urea_sl[sl] * leach_fact_doc;
560 LEACH_DOWN( nh4_ae_sl[sl], nh4_ae_sl[sl_plus], leach_fact_nh4);
561 LEACH_DOWN( nh4_an_sl[sl], nh4_an_sl[sl_plus], leach_fact_nh4);
562 LEACH_DOWN( sc_.coated_nh4_sl[sl], sc_.coated_nh4_sl[sl_plus], leach_fact_nh4);
563 LEACH_DOWN( sc_.nh3_liq_sl[sl], sc_.nh3_liq_sl[sl_plus], leach_fact_doc);
564 LEACH_DOWN( sc_.urea_sl[sl], sc_.urea_sl[sl_plus], leach_fact_doc);
565
566 sc_.accumulated_n_no3_leaching_sl[sl] += (no3_ae_sl[sl]+no3_an_sl[sl]) * leach_fact_no3;
567 LEACH_DOWN( no3_ae_sl[sl], no3_ae_sl[sl_plus], leach_fact_no3);
568 LEACH_DOWN( no3_an_sl[sl], no3_an_sl[sl_plus], leach_fact_no3);
569
570 accumulated_n_don_leaching_sl[sl] += (don_ae_sl[sl] + don_an_sl[sl]) * leach_fact_doc;
571 LEACH_DOWN( don_ae_sl[sl], don_ae_sl[sl_plus], leach_fact_doc);
572 LEACH_DOWN( don_an_sl[sl], don_an_sl[sl_plus], leach_fact_doc);
573 LEACH_DOWN( sc_.doc_sl[sl], sc_.doc_sl[sl_plus], leach_fact_doc);
574 LEACH_DOWN( sc_.an_doc_sl[sl], sc_.an_doc_sl[sl_plus], leach_fact_doc);
575 LEACH_DOWN( ae_acetate_sl[sl], ae_acetate_sl[sl_plus], leach_fact_doc);
576 LEACH_DOWN( an_acetate_sl[sl], an_acetate_sl[sl_plus], leach_fact_doc);
577
578 accumulated_n_no_leaching_sl[sl] += (no_liq_sl[sl]+an_no_liq_sl[sl]) * leach_fact_dissolved_gases;
579 accumulated_n_n2o_leaching_sl[sl] += (n2o_liq_sl[sl]+an_n2o_liq_sl[sl]) * leach_fact_dissolved_gases;
580 LEACH_DOWN( no_liq_sl[sl], no_liq_sl[sl_plus], leach_fact_dissolved_gases);
581 LEACH_DOWN( an_no_liq_sl[sl], an_no_liq_sl[sl_plus], leach_fact_dissolved_gases);
582 LEACH_DOWN( n2o_liq_sl[sl], n2o_liq_sl[sl_plus], leach_fact_dissolved_gases);
583 LEACH_DOWN( an_n2o_liq_sl[sl], an_n2o_liq_sl[sl_plus], leach_fact_dissolved_gases);
584 LEACH_DOWN( o2_liq_sl[sl], o2_liq_sl[sl_plus], leach_fact_dissolved_gases);
585
586 LEACH_DOWN( ch4_liq_sl[sl], ch4_liq_sl[sl_plus], leach_fact_dissolved_gases);
587 LEACH_DOWN( co2_liq_sl[sl], co2_liq_sl[sl_plus], leach_fact_dissolved_gases);
588
589 LEACH_DOWN( sc_.so4_sl[sl], sc_.so4_sl[sl_plus], leach_fact_no3);
590 LEACH_DOWN( sc_.ni_sl[sl], sc_.ni_sl[sl_plus], leach_fact_doc);
591 LEACH_DOWN( sc_.ui_sl[sl], sc_.ui_sl[sl_plus], leach_fact_doc);
592
593 if ( have_radon_diffusion)
594 {
595 LEACH_DOWN( radon_liq_sl[sl], radon_liq_sl[sl_plus], leach_fact_dissolved_gases);
596 }
597 }
598 }
599}

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_liq_diffusion()

void ldndc::SoilChemistryMeTrX::MeTrX_liq_diffusion ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_manure()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_manure ( )
private
Parameters
[in]None
[out]None
Returns
error code
319{
320 EventAttributes const * ev_manure = NULL;
321 while (( ev_manure = m_ManureEvents.pop()) != NULL)
322 {
323 double new_manure_n( -sc_.accumulated_n_fertilizer);
324 double new_manure_c( -sc_.accumulated_c_fertilizer);
325
326 double me_c = ev_manure->get( "/carbon", -1.0);
327 if ( cbm::flt_less( me_c, 0.0))
328 {
329 KLOGERROR( "manure event: carbon and nitrogen amount must be greater 0",
330 " [carbon=",me_c,"]");
331 return LDNDC_ERR_FAIL;
332 }
333 double me_cn = ev_manure->get( "/carbon-nitrogen-ratio", -1.0);
334 if ( cbm::flt_less( me_cn, 0.0))
335 {
336 KLOGERROR( "manure event: carbon/nitrogen ratio must be greater 0",
337 " [carbon/nitrogen ratio=",me_cn,"]");
338 return LDNDC_ERR_FAIL;
339 }
340
341 double add_c( me_c * cbm::HA_IN_M2);
342 double add_n( add_c / me_cn);
343
344 sc_.accumulated_c_fertilizer += add_c;
345 sc_.accumulated_n_fertilizer += add_n;
346
347 double add_n_nh4( 0.0);
348 double add_n_no3( 0.0);
349 double add_n_don( 0.0);
350 double add_n_urea( 0.0);
351
352 double add_c_doc( 0.0);
353
354 double add_c_aorg( 0.0);
355 double add_n_aorg( 0.0);
356
357 double add_c_lit_1( 0.0);
358 double add_c_lit_2( 0.0);
359 double add_c_lit_3( 0.0);
360
361 double add_n_lit_1( 0.0);
362 double add_n_lit_2( 0.0);
363 double add_n_lit_3( 0.0);
364
365 double ph_manure = ev_manure->get( "/ph", -1.0);
366
367 cbm::string_t const & manure = ev_manure->get( "/type", "-");
368 if ( manure == "slurry" )
369 {
370 double const avail_n = ev_manure->get( "/nitrogen-available", sipar_.FRAC_LABILE_N_SLURRY());
371 if ( !cbm::flt_greater_zero( avail_n))
372 {
373 KLOGERROR( "manure event (",manure,"): fraction of available nitrogen must be at least 0",
374 " [available nitrogen=",avail_n,"]");
375 return LDNDC_ERR_FAIL;
376 }
377 double const avail_c = ev_manure->get( "/carbon-available", sipar_.FRAC_LABILE_C_SLURRY());
378 if ( !cbm::flt_greater_zero( avail_c))
379 {
380 KLOGERROR( "manure event (",manure,"): fraction of available carbon must be at least 0",
381 " [available carbon=",avail_c,"]");
382 return LDNDC_ERR_FAIL;
383 }
384
385 double const liq_n = avail_n * add_n;
386 double const f_urea = ev_manure->get( "/urea-fraction", sipar_.LIQUREA_SLURRY());
387 add_n_urea = f_urea * liq_n;
388 double const f_nh4 = ev_manure->get( "/nh4-fraction", sipar_.LIQNH4_SLURRY());
389 add_n_nh4 = f_nh4 * liq_n;
390 double const f_don = ev_manure->get( "/don-fraction", sipar_.LIQDON_SLURRY());
391 add_n_don = f_don * liq_n;
392 double const f_no3 = ev_manure->get( "/no3-fraction", sipar_.LIQNO3_SLURRY());
393 add_n_no3 = f_no3 * liq_n;
394
395 if (cbm::flt_not_equal_zero( add_n_urea + add_n_nh4 + add_n_don + add_n_no3 - liq_n))
396 {
397 KLOGERROR( "manure event (",manure,"): fractions of liquid nitrogen do not add up to 1.0!",
398 " check UREA fraction, NH4 fraction, DON fraction and NO3 fraction");
399 return LDNDC_ERR_FAIL;
400 }
401
402 add_c_doc = avail_c * add_c;
403
404 double const add_c_res( add_c - add_c_doc);
405 double const add_n_res( add_n - add_n_don - add_n_nh4 - add_n_no3 - add_n_urea);
406
407 double const f_lignin = ev_manure->get( "/lignin-fraction", 0.2); // Bhogal et al. (2011), Levi-Minzi et al. (1986), Probert et al. (2005)
408 double const frac_c_lit_3( f_lignin);
409 double const f_cellulose = ev_manure->get( "/cellulose-fraction", 0.6); // Bhogal et al. (2011), Levi-Minzi et al. (1986)
410 double const frac_c_lit_2( f_cellulose);
411 double const frac_c_lit_1( 1.0 - frac_c_lit_2 - frac_c_lit_3);
412
413 if (( f_lignin + f_cellulose) > 1.0)
414 {
415 KLOGERROR( "manure event (",manure,"): fractions of litter do not add up to 1.0!",
416 " check lignin fraction and cellulose fraction");
417 return LDNDC_ERR_FAIL;
418 }
419
420 add_c_lit_1 += ( frac_c_lit_1 * add_c_res);
421 add_c_lit_2 += ( frac_c_lit_2 * add_c_res);
422 add_c_lit_3 += ( frac_c_lit_3 * add_c_res);
423
424 add_n_lit_1 += ( frac_c_lit_1 * add_n_res);
425 add_n_lit_2 += ( frac_c_lit_2 * add_n_res);
426 add_n_lit_3 += ( frac_c_lit_3 * add_n_res);
427 }
428 else if ( manure == "green" )
429 {
430 add_c_lit_1 = 0.2 * add_c;
431 add_c_lit_2 = 0.7 * add_c;
432 add_c_lit_3 = 0.1 * add_c;
433
434 add_n_lit_1 = 0.2 * add_n;
435 add_n_lit_2 = 0.7 * add_n;
436 add_n_lit_3 = 0.1 * add_n;
437 }
438 else if ( manure == "straw" )
439 {
440 add_c_lit_1 = 0.2 * add_c;
441 add_c_lit_2 = 0.7 * add_c;
442 add_c_lit_3 = 0.1 * add_c;
443
444 add_n_lit_1 = 0.2 * add_n;
445 add_n_lit_2 = 0.7 * add_n;
446 add_n_lit_3 = 0.1 * add_n;
447 }
448 else if ( manure == "farmyard" )
449 {
450 double const avail_n = ev_manure->get( "/nitrogen-available", sipar_.FRAC_LABILE_N_FARMYARD());
451 if ( !cbm::flt_greater_zero( avail_n))
452 {
453 KLOGERROR( "manure event (",manure,"): fraction of available nitrogen must be at least 0",
454 " [available nitrogen=",avail_n,"]");
455 return LDNDC_ERR_FAIL;
456 }
457 double const avail_c = ev_manure->get( "/carbon-available", sipar_.FRAC_LABILE_C_FARMYARD());
458 if ( !cbm::flt_greater_zero( avail_c))
459 {
460 KLOGERROR( "manure event (",manure,"): fraction of available carbon must be at least 0",
461 " [available carbon=",avail_c,"]");
462 return LDNDC_ERR_FAIL;
463 }
464
465 double const liq_n = avail_n * add_n;
466 double const f_urea = ev_manure->get( "/urea-fraction", sipar_.LIQUREA_FARMYARD());
467 add_n_urea = f_urea * liq_n;
468 double const f_nh4 = ev_manure->get( "/nh4-fraction", sipar_.LIQNH4_FARMYARD());
469 add_n_nh4 = f_nh4 * liq_n;
470 double const f_don = ev_manure->get( "/don-fraction", sipar_.LIQDON_FARMYARD());
471 add_n_don = f_don * liq_n;
472 double const f_no3 = ev_manure->get( "/no3-fraction", sipar_.LIQNO3_FARMYARD());
473 add_n_no3 = f_no3 * liq_n;
474
475 if (cbm::flt_not_equal_zero( add_n_urea + add_n_nh4 + add_n_don + add_n_no3 - liq_n))
476 {
477 KLOGERROR( "manure event (",manure,"): fractions of liquid nitrogen do not add up to 1.0!",
478 " check UREA fraction, NH4 fraction, DON fraction and NO3 fraction");
479 return LDNDC_ERR_FAIL;
480 }
481
482 add_c_doc = avail_c * add_c;
483
484 double const add_c_res( add_c - add_c_doc);
485 double const add_n_res( add_n - add_n_don - add_n_nh4 - add_n_no3 - add_n_urea);
486
487 double const f_lignin = ev_manure->get( "/lignin-fraction", 0.2); // Bhogal et al. (2011), Levi-Minzi et al. (1986), Probert et al. (2005)
488 double const frac_c_lit_3( f_lignin);
489 double const f_cellulose = ev_manure->get( "/cellulose-fraction", 0.6); // Bhogal et al. (2011), Levi-Minzi et al. (1986)
490 double const frac_c_lit_2( f_cellulose);
491 double const frac_c_lit_1( 1.0 - frac_c_lit_2 - frac_c_lit_3);
492
493 if (( f_lignin + f_cellulose) > 1.0)
494 {
495 KLOGERROR( "manure event (",manure,"): fractions of litter do not add up to 1.0!",
496 " check lignin fraction and cellulose fraction");
497 return LDNDC_ERR_FAIL;
498 }
499
500 add_c_lit_1 += ( frac_c_lit_1 * add_c_res);
501 add_c_lit_2 += ( frac_c_lit_2 * add_c_res);
502 add_c_lit_3 += ( frac_c_lit_3 * add_c_res);
503
504 add_n_lit_1 += ( frac_c_lit_1 * add_n_res);
505 add_n_lit_2 += ( frac_c_lit_2 * add_n_res);
506 add_n_lit_3 += ( frac_c_lit_3 * add_n_res);
507 }
508 else if ( manure == "compost" )
509 {
510 double const avail_n = ev_manure->get( "/nitrogen-available", sipar_.FRAC_LABILE_N_COMPOST());
511 if ( avail_n < 0.0)
512 {
513 KLOGERROR( "manure event (",manure,"): fraction of available nitrogen must be at least 0",
514 " [available nitrogen=",avail_n,"]");
515 return LDNDC_ERR_FAIL;
516 }
517 double const avail_c = ev_manure->get( "/carbon-available", sipar_.FRAC_LABILE_C_COMPOST());
518 if ( avail_c < 0.0)
519 {
520 KLOGERROR( "manure event (",manure,"): fraction of available carbon must be at least 0",
521 " [available carbon=",avail_c,"]");
522 return LDNDC_ERR_FAIL;
523 }
524
525 double const liq_n = avail_n * add_n;
526 double const f_urea = ev_manure->get( "/urea-fraction", sipar_.LIQUREA_COMPOST());
527 add_n_urea = f_urea * liq_n;
528 double const f_nh4 = ev_manure->get( "/nh4-fraction", sipar_.LIQNH4_COMPOST());
529 add_n_nh4 = f_nh4 * liq_n;
530 double const f_don = ev_manure->get( "/don-fraction", sipar_.LIQDON_COMPOST());
531 add_n_don = f_don * liq_n;
532 double const f_no3 = ev_manure->get( "/no3-fraction", sipar_.LIQNO3_COMPOST());
533 add_n_no3 = f_no3 * liq_n;
534
535 if (cbm::flt_not_equal_zero( add_n_urea+add_n_nh4+add_n_don+add_n_no3-liq_n))
536 {
537 KLOGERROR( "manure event (",manure,"): fractions of liquid nitrogen do not add up to 1.0!",
538 " check UREA fraction, NH4 fraction, DON fraction and NO3 fraction");
539 return LDNDC_ERR_FAIL;
540 }
541
542 add_c_doc = ( avail_c * add_c);
543
544 double const add_c_res( add_c - add_c_doc);
545 double const add_n_res( add_n - add_n_don - add_n_nh4 - add_n_no3 - add_n_urea);
546
547 double const f_lignin = ev_manure->get( "/lignin-fraction", 0.8);
548 double const frac_c_lit_3( f_lignin);
549 double const f_cellulose = ev_manure->get( "/cellulose-fraction", 0.1);
550 double const frac_c_lit_2( f_cellulose);
551 double const frac_c_lit_1( 1.0 - frac_c_lit_2 - frac_c_lit_3);
552
553 if (( f_lignin + f_cellulose) > 1.0)
554 {
555 KLOGERROR( "manure event (",manure,"): fractions of litter do not add up to 1.0!",
556 " check lignin fraction and cellulose fraction");
557 return LDNDC_ERR_FAIL;
558 }
559
560 add_c_lit_1 += ( frac_c_lit_1 * add_c_res);
561 add_c_lit_2 += ( frac_c_lit_2 * add_c_res);
562 add_c_lit_3 += ( frac_c_lit_3 * add_c_res);
563
564 add_n_lit_1 += ( frac_c_lit_1 * add_n_res);
565 add_n_lit_2 += ( frac_c_lit_2 * add_n_res);
566 add_n_lit_3 += ( frac_c_lit_3 * add_n_res);
567 }
568 else if ( manure == "generic" )
569 {
570 double const avail_n_default( (sipar_.FRAC_LABILE_N_SLURRY() + sipar_.FRAC_LABILE_N_FARMYARD()) / 2.0);
571 double const avail_n = ev_manure->get( "/nitrogen-available", avail_n_default);
572 if ( !cbm::flt_greater_zero( avail_n))
573 {
574 KLOGERROR( "manure event (",manure,"): fraction of available nitrogen must be at least 0",
575 " [available nitrogen=",avail_n,"]");
576 return LDNDC_ERR_FAIL;
577 }
578 double const avail_c_default( (sipar_.FRAC_LABILE_C_SLURRY() + sipar_.FRAC_LABILE_C_FARMYARD()) / 2.0);
579 double const avail_c = ev_manure->get( "/carbon-available", avail_c_default);
580 if ( !cbm::flt_greater_zero( avail_c))
581 {
582 KLOGERROR( "manure event (",manure,"): fraction of available carbon must be at least 0",
583 " [available carbon=",avail_c,"]");
584 return LDNDC_ERR_FAIL;
585 }
586
587 double const liq_n = avail_n * add_n;
588
589 double const f_urea_default( (sipar_.LIQUREA_SLURRY() + sipar_.LIQUREA_FARMYARD()) / 2.0);
590 double const f_urea = ev_manure->get( "/urea-fraction", f_urea_default);
591 add_n_urea = f_urea * liq_n;
592
593 double const f_nh4_default( (sipar_.LIQNH4_SLURRY() + sipar_.LIQNH4_FARMYARD()) / 2.0);
594 double const f_nh4 = ev_manure->get( "/nh4-fraction", f_nh4_default);
595 add_n_nh4 = f_nh4 * liq_n;
596
597 double const f_don_default( (sipar_.LIQDON_SLURRY() + sipar_.LIQDON_FARMYARD()) / 2.0);
598 double const f_don = ev_manure->get( "/don-fraction", f_don_default);
599 add_n_don = f_don * liq_n;
600
601 double const f_no3_default( (sipar_.LIQNO3_SLURRY() + sipar_.LIQNO3_FARMYARD()) / 2.0);
602 double const f_no3 = ev_manure->get( "/no3-fraction", f_no3_default);
603 add_n_no3 = f_no3 * liq_n;
604
605 if (cbm::flt_not_equal_zero( add_n_urea + add_n_nh4 + add_n_don + add_n_no3 - liq_n))
606 {
607 KLOGERROR( "manure event (",manure,"): fractions of liquid nitrogen do not add up to 1.0!",
608 " check UREA fraction, NH4 fraction, DON fraction and NO3 fraction");
609 return LDNDC_ERR_FAIL;
610 }
611
612 add_c_doc = avail_c * add_c;
613
614 double const add_c_res( add_c - add_c_doc);
615 double const add_n_res( add_n - add_n_don - add_n_nh4 - add_n_no3 - add_n_urea);
616
617 double const f_lignin = ev_manure->get( "/lignin-fraction", 0.2);
618 double const frac_c_lit_3( f_lignin);
619 double const f_cellulose = ev_manure->get( "/cellulose-fraction", 0.6);
620 double const frac_c_lit_2( f_cellulose);
621 double const frac_c_lit_1( 1.0 - frac_c_lit_2 - frac_c_lit_3);
622
623 if (( f_lignin + f_cellulose) > 1.0)
624 {
625 KLOGERROR( "manure event (",manure,"): fractions of litter do not add up to 1.0!",
626 " check lignin fraction and cellulose fraction");
627 return LDNDC_ERR_FAIL;
628 }
629
630 add_c_lit_1 += ( frac_c_lit_1 * add_c_res);
631 add_c_lit_2 += ( frac_c_lit_2 * add_c_res);
632 add_c_lit_3 += ( frac_c_lit_3 * add_c_res);
633
634 add_n_lit_1 += ( frac_c_lit_1 * add_n_res);
635 add_n_lit_2 += ( frac_c_lit_2 * add_n_res);
636 add_n_lit_3 += ( frac_c_lit_3 * add_n_res);
637 }
638 else
639 {
640 KLOGWARN( "Unknown manure type \"",manure,"\". Skipping event!");
641 break;
642 }
643
644 double const depth( ev_manure->get( "/depth", 0.0));
645
646 size_t l_0 = 0;
647 size_t l_1 = 1;
648 if ( cbm::flt_equal_zero( depth))
649 {
650 l_0 = 0;
651 l_1 = 1;
652 for( size_t sl = 1; sl < sl_.soil_layer_cnt(); ++sl)
653 {
654 if ( sc_.depth_sl[sl] <= 0.01)
655 {
656 l_1 = sl;
657 }
658 else
659 {
660 break;
661 }
662 }
663 }
664 else
665 {
666 //l_0 not allowed to be deeper than last but one soil layer
667 l_0 = sl_.soil_layer_cnt()-2;
668 //find first layer (from top) having at least depth <depth(fert)>
669 for ( size_t l = 0; l < sl_.soil_layer_cnt()-1; ++l)
670 {
671 if ( cbm::flt_greater_equal( sc_.depth_sl[l], depth))
672 {
673 l_0 = l;
674 break;
675 }
676 }
677 //l_1 must at least one layer below l_0
678 l_1 = l_0 + 1;
679 for ( size_t l = l_0 + 1; l < sl_.soil_layer_cnt(); ++l)
680 {
681 /* distribute at least among 4cm soil profile */
682 if ( cbm::flt_greater_equal( sc_.depth_sl[l], depth + 0.04))
683 {
684 l_1 = l;
685 break;
686 }
687 }
688 }
689
690 for ( size_t sl = l_0; sl < l_1; ++sl)
691 {
692 double const layer_fraction( 1.0 / double(l_1 - l_0));
693 if ( cbm::flt_greater_zero( ph_manure))
694 {
695 sc_.ph_sl[sl] = ph_manure;
696 }
697 double const layer_fraction_ae( (1.0 - sc_.anvf_sl[sl]) * layer_fraction);
698 double const layer_fraction_an( sc_.anvf_sl[sl] * layer_fraction);
699
700 don_ae_sl[sl] += add_n_don * layer_fraction_ae;
701 don_an_sl[sl] += add_n_don * layer_fraction_an;
702 nh4_ae_sl[sl] += add_n_nh4 * layer_fraction_ae;
703 nh4_an_sl[sl] += add_n_nh4 * layer_fraction_an;
704 no3_ae_sl[sl] += add_n_no3 * layer_fraction_ae;
705 no3_an_sl[sl] += add_n_no3 * layer_fraction_an;
706 sc_.urea_sl[sl] += add_n_urea * layer_fraction;
707
708 sc_.doc_sl[sl] += add_c_doc * layer_fraction_ae;
709 sc_.an_doc_sl[sl] += add_c_doc * layer_fraction_an;
710
711 sc_.C_aorg_sl[sl] += add_c_aorg * layer_fraction;
712 sc_.N_aorg_sl[sl] += add_n_aorg * layer_fraction;
713
714 sc_.C_lit1_sl[sl] += add_c_lit_1 * layer_fraction;
715 sc_.C_lit2_sl[sl] += add_c_lit_2 * layer_fraction;
716 sc_.C_lit3_sl[sl] += add_c_lit_3 * layer_fraction;
717
718 sc_.N_lit1_sl[sl] += add_n_lit_1 * layer_fraction;
719 sc_.N_lit2_sl[sl] += add_n_lit_2 * layer_fraction;
720 sc_.N_lit3_sl[sl] += add_n_lit_3 * layer_fraction;
721
722 accumulated_n_nh4_fertilization_sl[sl] += add_n_nh4 * layer_fraction;
723 accumulated_n_no3_fertilization_sl[sl] += add_n_no3 * layer_fraction;
724 accumulated_n_don_fertilization_sl[sl] += add_n_don * layer_fraction;
725 accumulated_n_urea_fertilization_sl[sl] += add_n_urea * layer_fraction;
726 accumulated_n_litter_fertilization_sl[sl] += (add_n_lit_1 + add_n_lit_2 + add_n_lit_3) * layer_fraction;
727 accumulated_n_aorg_fertilization_sl[sl] += add_n_aorg * layer_fraction;
728 }
729
730 cbm::state_scratch_t * mcom = io_kcomm->get_scratch();
731
732 new_manure_n += sc_.accumulated_n_fertilizer;
733 double old_manure_n( 0.0);
734 mcom->get( "manure:amountN", &old_manure_n, 0.0);
735 mcom->set( "manure:amountN", old_manure_n + (new_manure_n * cbm::M2_IN_HA));
736
737 new_manure_c += sc_.accumulated_c_fertilizer;
738 double old_manure_c( 0.0);
739 mcom->get( "manure:amountC", &old_manure_c, 0.0);
740 mcom->set( "manure:amountC", old_manure_c + (new_manure_c * cbm::M2_IN_HA));
741 }
742
743 return LDNDC_ERR_OK;
744}

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_metabolism()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_metabolism ( )
private
Parameters
[in]None
[out]None
Returns
error code
216{
217 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
218 {
219 double const metabolism_rate( 0.1 * FTS_TOT_);
220
221 double const mic_12( sc_.C_micro1_sl[sl] + sc_.C_micro2_sl[sl]);
222 double const mic_23( sc_.C_micro2_sl[sl] + sc_.C_micro3_sl[sl]);
223
224 if ( cbm::flt_greater_zero( mic_12))
225 {
226 double const fact_mic_12( sc_.anvf_sl[sl]);
227 double trans_12( (fact_mic_12 * mic_12 - sc_.C_micro2_sl[sl]) * metabolism_rate);
228 if ( cbm::flt_greater_zero( trans_12))
229 {
230 double const trans_max( cbm::bound_min( 0.0, sc_.C_micro1_sl[sl] - MICRO_C_MIN));
231 trans_12 = cbm::bound_max( trans_12, trans_max);
232 sc_.C_micro1_sl[sl] -= trans_12;
233 sc_.C_micro2_sl[sl] += trans_12;
234 }
235 else
236 {
237 double const trans_max( cbm::bound_min( 0.0, sc_.C_micro2_sl[sl] - MICRO_C_MIN));
238 trans_12 = cbm::bound_max( -trans_12, trans_max);
239 sc_.C_micro2_sl[sl] -= trans_12;
240 sc_.C_micro1_sl[sl] += trans_12;
241 }
242 }
243
244 if ( cbm::flt_greater_zero( mic_23))
245 {
246 double const fact_mic_23( 1.0 - no3_an_sl[sl] / (no3_an_sl[sl] + (NO3_MOLAR_MAX_FE_RED * sc_.h_sl[sl] * M_N_SCALE)));
247 double trans_23( (fact_mic_23 * mic_23 - sc_.C_micro3_sl[sl]) * metabolism_rate);
248 if ( cbm::flt_greater_zero( trans_23))
249 {
250 double const trans_max( cbm::bound_min( 0.0, sc_.C_micro2_sl[sl] - MICRO_C_MIN));
251 trans_23 = cbm::bound_max( trans_23, trans_max);
252 sc_.C_micro2_sl[sl] -= trans_23;
253 sc_.C_micro3_sl[sl] += trans_23;
254 }
255 else
256 {
257 double const trans_max( cbm::bound_min( 0.0, sc_.C_micro3_sl[sl] - MICRO_C_MIN));
258 trans_23 = cbm::bound_max( -trans_23, trans_max);
259 sc_.C_micro3_sl[sl] -= trans_23;
260 sc_.C_micro2_sl[sl] += trans_23;
261 }
262 }
263 }
264 return LDNDC_ERR_OK;
265}

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_microbial_dynamics()

void ldndc::SoilChemistryMeTrX::MeTrX_microbial_dynamics ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_nh3_nh4_equilibrium()

void ldndc::SoilChemistryMeTrX::MeTrX_nh3_nh4_equilibrium ( )
private
Parameters
[in]None
[out]None
Returns
void
33{
34 if ( have_water_table)
35 {
36 double ph( MeTrX_get_ph_wl());
37 for ( size_t wl = 0; wl < sb_.surfacebulk_layer_cnt(); wl++)
38 {
39 double const k_a( pow( 10.0,(-2728.3 / (mc_temp_sl[0] + cbm::D_IN_K) - 0.094219))); // Sadeghi et al. (1988) (for 5 < ph < 10)
40
41 double const n_tot( sb_.nh4_sbl[wl] + sb_.nh3_sbl[wl]);
42 double const frac_nh3( cbm::bound_max( 1.0 / (1.0 + (pow(10.0, - ph) / k_a)), 0.99));
43
44 double const delta_nh3( frac_nh3 * n_tot - sb_.nh3_sbl[wl]);
45 if( cbm::flt_greater( delta_nh3, 0.0))
46 {
47 sb_.nh3_sbl[wl] += delta_nh3;
48 sb_.nh4_sbl[wl] = cbm::bound_min( 0.0, sb_.nh4_sbl[wl] - delta_nh3);
49 accumulated_n_nh4_nh3_conversion_sbl[wl] += delta_nh3;
50 }
51 else if( cbm::flt_less( delta_nh3, 0.0))
52 {
53 sb_.nh3_sbl[wl] = cbm::bound_min( 0.0, sb_.nh3_sbl[wl] + delta_nh3);
54 sb_.nh4_sbl[wl] -= delta_nh3;
55 accumulated_n_nh3_nh4_conversion_sbl[wl] -= delta_nh3;
56 }
57 }
58 }
59
60 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
61 {
62 double const k_a( pow( 10.0, -2728.3 / (mc_temp_sl[sl] + cbm::D_IN_K) - 0.094219));
63 double const nh4_tot( nh4_ae_sl[sl] + nh4_an_sl[sl]);
64 double const n_tot( nh4_tot + sc_.nh3_liq_sl[sl]);
65 double const frac_nh3( cbm::bound_max( 1.0 / (1.0 + (pow(10.0, - sc_.ph_sl[sl]) / k_a)), 0.99));
66
67 double const delta_nh3( frac_nh3 * n_tot - sc_.nh3_liq_sl[sl]);
68 if ( cbm::flt_greater( delta_nh3, 0.0))
69 {
70 sc_.nh3_liq_sl[sl] += delta_nh3;
71 double const delta_nh4_ae( nh4_ae_sl[sl] / nh4_tot * delta_nh3);
72 double const delta_nh4_an( delta_nh3 - delta_nh4_ae);
73 nh4_ae_sl[sl] = cbm::bound_min( 0.0, nh4_ae_sl[sl] - delta_nh4_ae);
74 nh4_an_sl[sl] = cbm::bound_min( 0.0, nh4_an_sl[sl] - delta_nh4_an);
75 accumulated_n_nh4_nh3_conversion_sl[sl] += delta_nh3;
76 }
77 else if ( cbm::flt_less( delta_nh3, 0.0))
78 {
79 sc_.nh3_liq_sl[sl] = cbm::bound_min( 0.0, sc_.nh3_liq_sl[sl] + delta_nh3);
80 nh4_ae_sl[sl] -= delta_nh3 * (1.0 - sc_.anvf_sl[sl]);
81 nh4_an_sl[sl] -= delta_nh3 * sc_.anvf_sl[sl];
82 accumulated_n_nh3_nh4_conversion_sl[sl] -= delta_nh3;
83 }
84
85 }
86}
double MeTrX_get_ph_wl()
Definition: soilchemistry-metrx-physics-chemistry.cpp:607

References MeTrX_get_ph_wl().

Referenced by solve().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ MeTrX_nitrification()

void ldndc::SoilChemistryMeTrX::MeTrX_nitrification ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_nitrogen_fertilizer_release()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_nitrogen_fertilizer_release ( )
private

Transforms nitrogen from slow release nitrogen fertilizer to nh4.

Parameters
[in]None
[out]None
Returns
void
1001{
1002 double const coated_nh4_sbl_sum( sb_.coated_nh4_sbl.sum());
1003 double const coated_nh4_sl_sum( sc_.coated_nh4_sl.sum());
1004 double const coated_nh4_sum( coated_nh4_sbl_sum + coated_nh4_sl_sum);
1005 if ( !cbm::flt_greater_zero( coated_nh4_sum))
1006 { return LDNDC_ERR_OK; }
1007
1008 if ( cbm::flt_greater_zero( coated_nh4_sbl_sum))
1009 {
1010 for ( size_t sbl = 0; sbl < sb_.surfacebulk_layer_cnt(); ++sbl)
1011 {
1012 crnf_.update_crnf( 1.0, mc_temp_sl[0], FTS_TOT_, sb_.nh4_sbl[sbl] / coated_nh4_sum);
1013 }
1014 }
1015
1016 if ( cbm::flt_greater_zero( coated_nh4_sl_sum))
1017 {
1018 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
1019 {
1020 crnf_.update_crnf( MeTrX_get_wfps( sl), mc_temp_sl[sl], FTS_TOT_, sc_.coated_nh4_sl[sl] / coated_nh4_sum);
1021 }
1022 }
1023
1024 double coated_nh4_release( crnf_.get_crnf_release( coated_nh4_sum));
1025 if ( !cbm::flt_greater_zero( coated_nh4_release))
1026 { return LDNDC_ERR_OK; }
1027
1028 double const scale( coated_nh4_release / coated_nh4_sum);
1029
1030 if ( cbm::flt_greater( scale, 0.99))
1031 {
1032 if ( cbm::flt_greater_zero( coated_nh4_sbl_sum))
1033 {
1034 for ( size_t sbl = 0; sbl < sb_.surfacebulk_layer_cnt(); ++sbl)
1035 {
1036 sb_.nh4_sbl[sbl] += sb_.coated_nh4_sbl[sbl];
1037 sb_.coated_nh4_sbl[sbl] = 0.0;
1038 }
1039 }
1040
1041 if ( cbm::flt_greater_zero( coated_nh4_sl_sum))
1042 {
1043 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
1044 {
1045 nh4_ae_sl[sl] += sc_.coated_nh4_sl[sl] * (1.0 - sc_.anvf_sl[sl]);
1046 nh4_an_sl[sl] += sc_.coated_nh4_sl[sl] * sc_.anvf_sl[sl];
1047 sc_.coated_nh4_sl[sl] = 0.0;
1048 }
1049 }
1050 }
1051 else
1052 {
1053 if ( cbm::flt_greater_zero( coated_nh4_sbl_sum))
1054 {
1055 for ( size_t sbl = 0; sbl < sb_.surfacebulk_layer_cnt(); ++sbl)
1056 {
1057 if ( cbm::flt_greater_zero( sb_.coated_nh4_sbl[sbl]))
1058 {
1059 double const n_transform( scale * sb_.coated_nh4_sbl[sbl]);
1060 sb_.coated_nh4_sbl[sbl] -= n_transform;
1061 sb_.nh4_sbl[sbl] += n_transform;
1062 }
1063 }
1064 }
1065
1066 if ( cbm::flt_greater_zero( coated_nh4_sl_sum))
1067 {
1068 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
1069 {
1070 if ( cbm::flt_greater_zero( sc_.coated_nh4_sl[sl]))
1071 {
1072 double const n_transform( scale * sc_.coated_nh4_sl[sl]);
1073 sc_.coated_nh4_sl[sl] -= n_transform;
1074 nh4_ae_sl[sl] += n_transform * (1.0 - sc_.anvf_sl[sl]);
1075 nh4_an_sl[sl] += n_transform * sc_.anvf_sl[sl];
1076 }
1077 }
1078 }
1079 }
1080
1081 return LDNDC_ERR_OK;
1082}

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_pertubation()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_pertubation ( )
private
Parameters
[in]None
[out]None
Returns
error code
1639{
1640 //Pertubation is only calculated once per day since it is a very slow process
1641 if ( lclock()->subday() == 1)
1642 {
1643 size_t sl_max_1( sl_.soil_layer_cnt()-1);
1644 double nmicro1_lowest_sl(n_micro_1_sl[sl_max_1]);
1645 double nmicro2_lowest_sl(n_micro_2_sl[sl_max_1]);
1646 double nmicro3_lowest_sl(n_micro_3_sl[sl_max_1]);
1647 double naorg_lowest_sl(sc_.N_aorg_sl[sl_max_1]);
1648 double nlit1_lowest_sl(sc_.N_lit1_sl[sl_max_1]);
1649 double nlit2_lowest_sl(sc_.N_lit2_sl[sl_max_1]);
1650 double nlit3_lowest_sl(sc_.N_lit3_sl[sl_max_1]);
1651 double nhum1_lowest_sl(n_humus_1_sl[sl_max_1]);
1652 double nhum2_lowest_sl(n_humus_2_sl[sl_max_1]);
1653 double nhum3_lowest_sl(n_humus_3_sl[sl_max_1]);
1654
1655 lerr_t rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, sc_.C_micro1_sl, sc_.h_sl, interface_delta_x_soil_sl);
1656 if ( rc){ return rc; }
1657 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, n_micro_1_sl, sc_.h_sl, interface_delta_x_soil_sl);
1658 if ( rc){ return rc; }
1659
1660 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, sc_.C_micro2_sl, sc_.h_sl, interface_delta_x_soil_sl);
1661 if ( rc){ return rc; }
1662 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, n_micro_2_sl, sc_.h_sl, interface_delta_x_soil_sl);
1663 if ( rc){ return rc; }
1664
1665 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, sc_.C_micro3_sl, sc_.h_sl, interface_delta_x_soil_sl);
1666 if ( rc){ return rc; }
1667 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, n_micro_3_sl, sc_.h_sl, interface_delta_x_soil_sl);
1668 if ( rc){ return rc; }
1669
1670 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, sc_.C_aorg_sl, sc_.h_sl, interface_delta_x_soil_sl);
1671 if ( rc){ return rc; }
1672 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, sc_.N_aorg_sl, sc_.h_sl, interface_delta_x_soil_sl);
1673 if ( rc){ return rc; }
1674
1675 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, sc_.C_lit1_sl, sc_.h_sl, interface_delta_x_soil_sl);
1676 if ( rc){ return rc; }
1677 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, sc_.N_lit1_sl, sc_.h_sl, interface_delta_x_soil_sl);
1678 if ( rc){ return rc; }
1679
1680 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, sc_.C_lit2_sl, sc_.h_sl, interface_delta_x_soil_sl);
1681 if ( rc){ return rc; }
1682 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, sc_.N_lit2_sl, sc_.h_sl, interface_delta_x_soil_sl);
1683 if ( rc){ return rc; }
1684
1685 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, sc_.C_lit3_sl, sc_.h_sl, interface_delta_x_soil_sl);
1686 if ( rc){ return rc; }
1687 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, sc_.N_lit3_sl, sc_.h_sl, interface_delta_x_soil_sl);
1688 if ( rc){ return rc; }
1689
1690 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, c_humus_1_sl, sc_.h_sl, interface_delta_x_soil_sl);
1691 if ( rc){ return rc; }
1692 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, n_humus_1_sl, sc_.h_sl, interface_delta_x_soil_sl);
1693 if ( rc){ return rc; }
1694
1695 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, c_humus_2_sl, sc_.h_sl, interface_delta_x_soil_sl);
1696 if ( rc){ return rc; }
1697 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, n_humus_2_sl, sc_.h_sl, interface_delta_x_soil_sl);
1698 if ( rc){ return rc; }
1699
1700 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, c_humus_3_sl, sc_.h_sl, interface_delta_x_soil_sl);
1701 if ( rc){ return rc; }
1702 rc = transport_.pertubation(1.0, D_eff_dailyturbation_sl, n_humus_3_sl, sc_.h_sl, interface_delta_x_soil_sl);
1703 if ( rc){ return rc; }
1704
1705 if ( output_writer_.write_fluxes())
1706 {
1707 /* nmicro */
1708 transport_.calculate_soil_perturbation_fluxes( sl_.soil_layer_cnt(), 1.0, sc_.h_sl, interface_delta_x_soil_sl, D_eff_dailyturbation_sl, n_micro_1_sl, nmicro1_lowest_sl, communicate_sl);
1709 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
1710 {
1711 accumulated_n_micro_perturbation_sl[sl] += communicate_sl[sl];
1712 }
1713 transport_.calculate_soil_perturbation_fluxes( sl_.soil_layer_cnt(), 1.0, sc_.h_sl, interface_delta_x_soil_sl, D_eff_dailyturbation_sl, n_micro_2_sl, nmicro2_lowest_sl, communicate_sl);
1714 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
1715 {
1716 accumulated_n_micro_perturbation_sl[sl] += communicate_sl[sl];
1717 }
1718 transport_.calculate_soil_perturbation_fluxes( sl_.soil_layer_cnt(), 1.0, sc_.h_sl, interface_delta_x_soil_sl, D_eff_dailyturbation_sl, n_micro_3_sl, nmicro3_lowest_sl, communicate_sl);
1719 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
1720 {
1721 accumulated_n_micro_perturbation_sl[sl] += communicate_sl[sl];
1722 }
1723
1724 /* naorg */
1725 transport_.calculate_soil_perturbation_fluxes( sl_.soil_layer_cnt(), 1.0, sc_.h_sl, interface_delta_x_soil_sl, D_eff_dailyturbation_sl, sc_.N_aorg_sl, naorg_lowest_sl, communicate_sl);
1726 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
1727 {
1728 accumulated_n_aorg_perturbation_sl[sl] += communicate_sl[sl];
1729 }
1730
1731 /*litter*/
1732 transport_.calculate_soil_perturbation_fluxes( sl_.soil_layer_cnt(), 1.0, sc_.h_sl, interface_delta_x_soil_sl, D_eff_dailyturbation_sl, sc_.N_lit1_sl, nlit1_lowest_sl, communicate_sl);
1733 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
1734 {
1735 accumulated_n_litter_perturbation_sl[sl] += communicate_sl[sl];
1736 }
1737 transport_.calculate_soil_perturbation_fluxes( sl_.soil_layer_cnt(), 1.0, sc_.h_sl, interface_delta_x_soil_sl, D_eff_dailyturbation_sl, sc_.N_lit2_sl, nlit2_lowest_sl, communicate_sl);
1738 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
1739 {
1740 accumulated_n_litter_perturbation_sl[sl] += communicate_sl[sl];
1741 }
1742 transport_.calculate_soil_perturbation_fluxes( sl_.soil_layer_cnt(), 1.0, sc_.h_sl, interface_delta_x_soil_sl, D_eff_dailyturbation_sl, sc_.N_lit3_sl, nlit3_lowest_sl, communicate_sl);
1743 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
1744 {
1745 accumulated_n_litter_perturbation_sl[sl] += communicate_sl[sl];
1746 }
1747
1748 /*humus*/
1749 transport_.calculate_soil_perturbation_fluxes( sl_.soil_layer_cnt(), 1.0, sc_.h_sl, interface_delta_x_soil_sl, D_eff_dailyturbation_sl, n_humus_1_sl, nhum1_lowest_sl, communicate_sl);
1750 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
1751 {
1752 accumulated_n_humus_1_perturbation_sl[sl] += communicate_sl[sl];
1753 }
1754 transport_.calculate_soil_perturbation_fluxes( sl_.soil_layer_cnt(), 1.0, sc_.h_sl, interface_delta_x_soil_sl, D_eff_dailyturbation_sl, n_humus_2_sl, nhum2_lowest_sl, communicate_sl);
1755 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
1756 {
1757 accumulated_n_humus_2_perturbation_sl[sl] += communicate_sl[sl];
1758 }
1759 transport_.calculate_soil_perturbation_fluxes( sl_.soil_layer_cnt(), 1.0, sc_.h_sl, interface_delta_x_soil_sl, D_eff_dailyturbation_sl, n_humus_3_sl, nhum3_lowest_sl, communicate_sl);
1760 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
1761 {
1762 accumulated_n_humus_3_perturbation_sl[sl] += communicate_sl[sl];
1763 }
1764 }
1765 }
1766 return LDNDC_ERR_OK;
1767}

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_pH_calculation()

void ldndc::SoilChemistryMeTrX::MeTrX_pH_calculation ( )
private
Parameters
[in]None
[out]None
Returns
void
622{
623 for ( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
624 {
625 sc_.ph_sl[sl] = MeTrX_get_ph_sl( sl);
626 }
627}
double MeTrX_get_ph_sl(size_t)
Returns dynamic pH-value of given soil layer.
Definition: soilchemistry-metrx-physics-chemistry.cpp:599

References MeTrX_get_ph_sl().

Referenced by solve().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ MeTrX_physics()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_physics ( )
private
Parameters
[in]None
[out]None
Returns
error code

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_radon_source_sink()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_radon_source_sink ( )
private
Parameters
[in]None
[out]None
Returns
error code
471{
472 if ( have_radon_diffusion)
473 {
474 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
475 {
476 //timestep in seconds
477 double const Delta_t( 3600 * 24.0 / (double)TOTAL_TIME_STEPS );
478
479 //emanation coefficient
480 double emanation_coeff( sc_.sand_sl[sl] * radon_emanation_coeff( sl,
481 sipar_.METRX_RADON_EMANATION_SAND_EPS0(),
482 sipar_.METRX_RADON_EMANATION_SAND_A(),
483 sipar_.METRX_RADON_EMANATION_SAND_B(),
484 sipar_.METRX_RADON_EMANATION_SAND_C())
485 + sc_.silt_sl[sl] * radon_emanation_coeff( sl,
486 sipar_.METRX_RADON_EMANATION_SILT_EPS0(),
487 sipar_.METRX_RADON_EMANATION_SILT_A(),
488 sipar_.METRX_RADON_EMANATION_SILT_B(),
489 sipar_.METRX_RADON_EMANATION_SILT_C())
490 + sc_.clay_sl[sl] * radon_emanation_coeff( sl, sipar_.METRX_RADON_EMANATION_CLAY_EPS0(),
491 sipar_.METRX_RADON_EMANATION_CLAY_A(),
492 sipar_.METRX_RADON_EMANATION_CLAY_B(),
493 sipar_.METRX_RADON_EMANATION_CLAY_C()));
494
495 //radon source/sink term: creation of radon-222 via the decay of radium-226
496 // and its radioactive decay
497 radon_gas_sl[sl] += sipar_.METRX_RADON_DECAY_CONST() * Delta_t * sc_.radium_sl[sl] * sc_.get_soil_mass( sl) * emanation_coeff
498 - Delta_t * sipar_.METRX_RADON_DECAY_CONST() * radon_gas_sl[sl];
499
500 //radon sink term: radioactive decay of radon
501 //radon_gas_sl[sl] -= Delta_t * sipar_.METRX_RADON_DECAY_CONST() * radon_gas_sl[sl];
502 radon_liq_sl[sl] -= Delta_t * sipar_.METRX_RADON_DECAY_CONST() * radon_liq_sl[sl];
503 }
504 }
505 return LDNDC_ERR_OK;
506}

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_receive_state()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_receive_state ( )
private
Parameters
[in]None
[out]None
Returns
error code
261{
262 for ( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
263 {
264 if ( cbm::flt_greater_zero( sc_.nh4_sl[sl]))
265 {
266 double const nh4_old( nh4_ae_sl[sl] + nh4_an_sl[sl]);
267 if ( cbm::flt_greater_zero( nh4_old))
268 {
269 nh4_ae_sl[sl] = cbm::bound_min( 0.0, nh4_ae_sl[sl] / nh4_old * sc_.nh4_sl[sl]);
270 nh4_an_sl[sl] = cbm::bound_min( 0.0, sc_.nh4_sl[sl] - nh4_ae_sl[sl]);
271 }
272 else
273 {
274 nh4_ae_sl[sl] = (1.0 - sc_.anvf_sl[sl]) * sc_.nh4_sl[sl];
275 nh4_an_sl[sl] = sc_.anvf_sl[sl] * sc_.nh4_sl[sl];
276 }
277 }
278 else
279 {
280 nh4_ae_sl[sl] = 0.0;
281 nh4_an_sl[sl] = 0.0;
282 }
283
284 if ( cbm::flt_greater_zero( sc_.don_sl[sl]))
285 {
286 double const don_old( don_ae_sl[sl] + don_an_sl[sl]);
287 if ( cbm::flt_greater_zero( don_old))
288 {
289 don_ae_sl[sl] = cbm::bound_min( 0.0, don_ae_sl[sl] / don_old * sc_.don_sl[sl]);
290 don_an_sl[sl] = cbm::bound_min( 0.0, sc_.don_sl[sl] - don_ae_sl[sl]);
291 }
292 else
293 {
294 don_ae_sl[sl] = (1.0 - sc_.anvf_sl[sl]) * sc_.don_sl[sl];
295 don_an_sl[sl] = sc_.anvf_sl[sl] * sc_.don_sl[sl];
296 }
297 }
298 else
299 {
300 don_ae_sl[sl] = 0.0;
301 don_an_sl[sl] = 0.0;
302 }
303
304 double no3_tot( sc_.no3_sl[sl] + sc_.an_no3_sl[sl]);
305 if ( cbm::flt_greater_zero( no3_tot))
306 {
307 double const no3_old( no3_ae_sl[sl] + no3_an_sl[sl]);
308 if ( cbm::flt_greater_zero( no3_old))
309 {
310 no3_ae_sl[sl] = cbm::bound_min( 0.0, no3_ae_sl[sl] / no3_old * no3_tot);
311 no3_an_sl[sl] = cbm::bound_min( 0.0, no3_tot - no3_ae_sl[sl]);
312 }
313 else
314 {
315 no3_ae_sl[sl] = (1.0 - sc_.anvf_sl[sl]) * no3_tot;
316 no3_an_sl[sl] = sc_.anvf_sl[sl] * no3_tot;
317 }
318 }
319 else
320 {
321 no3_ae_sl[sl] = 0.0;
322 no3_an_sl[sl] = 0.0;
323 }
324 }
325
326 return LDNDC_ERR_OK;
327}

Referenced by MeTrX_update().

Here is the caller graph for this function:

◆ MeTrX_reset()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_reset ( )
private
Parameters
[in]None
[out]None
Returns
void
186{
187 co2_auto_sl = 0.0;
188 co2_hetero_sl = 0.0;
189
190 if ( timemode_ == TMODE_SUBDAILY)
191 {
192 if ( lclock()->is_position( TMODE_PRE_DAILY))
193 {
196 }
197 }
198 else
199 {
202 }
203
204 return LDNDC_ERR_OK;
205}
lerr_t MeTrX_reset_subdaily()
Definition: soilchemistry-metrx-reset.cpp:213
lerr_t MeTrX_reset_daily()
Definition: soilchemistry-metrx-reset.cpp:265

References MeTrX_reset_daily(), and MeTrX_reset_subdaily().

Referenced by solve().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ MeTrX_reset_daily()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_reset_daily ( )
private
Parameters
[in]None
[out]None
Returns
void
266{
267 /* Soil layer variables */
268 for (size_t sl = 0; sl < sl_.soil_layer_cnt(); sl++)
269 {
270 plant_o2_consumption_sl[sl] = 0.0;
271
272 day_nitrify_n2o_sl[sl] = 0.0;
273 day_nit_no2_no3_sl[sl] = 0.0;
274
275 day_acetate_cons_fe3_sl[sl] = 0.0;
276 day_h2_c_eq_cons_fe3_sl[sl] = 0.0;
277 day_fe2_oxidation_sl[sl] = 0.0;
278
279 day_acetate_prod_sl[sl] = 0.0;
280
281 day_ch4_oxidation_sl[sl] = 0.0;
282
283 day_h2_c_eq_prod_sl[sl] = 0.0;
284 day_ch4_production_acetate_sl[sl] = 0.0;
285 day_ch4_production_hydrogen_sl[sl] = 0.0;
286
287 day_doc_prod_sl[sl] = 0.0;
288 day_denit_factor_c_sl[sl] = 0.0;
289 day_denit_factor_n_sl[sl] = 0.0;
290 }
291
292 // Groundwater access
293 day_no3_groundwater_access = 0.0;
294
295 // Mineralisation
296 day_min_n_decomp = 0.0;
297 day_min_n_aorg = 0.0;
298 day_min_n_mic_1 = 0.0;
299 day_min_n_mic_2 = 0.0;
300 day_min_n_mic_3 = 0.0;
301
302 // Assimilation
303 day_assi_n_mic_1 = 0.0;
304 day_assi_n_mic_2 = 0.0;
305 day_assi_n_mic_3 = 0.0;
306 day_assi_c_mic_1 = 0.0;
307 day_assi_c_mic_2 = 0.0;
308 day_assi_c_mic_3 = 0.0;
309
310 // Nitrification
311 day_nit_nh4_no2 = 0.0;
312 day_nit_no2_no = 0.0;
313 day_nit_no2_n2o = 0.0;
314 day_nit_no2_no3_sl = 0.0;
315
316 // Denitrification
317 day_denit_no3_no2 = 0.0;
318 day_denit_no2_no = 0.0;
319 day_denit_no2_n2o = 0.0;
320 day_denit_no2_n2 = 0.0;
321 day_denit_no_n2o = 0.0;
322 day_denit_no_n2 = 0.0;
323 day_denit_n2o_n2 = 0.0;
324 day_chemodenit_no2_no = 0.0;
325
326 // Respiration / Fermentation / Methanogenesis
327 day_co2_prod_mic_1_growth = 0.0;
328 day_co2_prod_mic_1_maintenance = 0.0;
329 day_co2_prod_mic_2 = 0.0;
330 day_co2_prod_mic_3_acetate_prod = 0.0;
331 day_co2_prod_mic_3_acetate_cons = 0.0;
332 day_co2_prod_ch4_prod = 0.0;
333 day_co2_prod_ch4_cons = 0.0;
334
335 // Leaching
336 day_leach_o2 = 0.0;
337 day_leach_n2o = 0.0;
338 day_leach_n2 = 0.0;
339 day_leach_no = 0.0;
340 day_leach_nh3 = 0.0;
341 day_leach_urea = 0.0;
342 day_leach_radon = 0.0;
343
344 // litter
345 dC_root_exsudates = 0.0;
346 dC_litter_algae = 0.0;
347
348 // Decomposition
349 day_decomp_c_lit_1 = 0.0;
350 day_decomp_c_lit_2 = 0.0;
351 day_decomp_c_lit_3 = 0.0;
352 day_decomp_n_lit_1 = 0.0;
353 day_decomp_n_lit_2 = 0.0;
354 day_decomp_n_lit_3 = 0.0;
355 day_decomp_c_hum_1_sl = 0.0;
356 day_decomp_c_hum_2_sl = 0.0;
357 day_decomp_c_hum_3_sl = 0.0;
358 day_decay_c_mic_sl = 0.0;
359 day_decomp_n_hum_1 = 0.0;
360 day_decomp_n_hum_2 = 0.0;
361 day_decomp_n_hum_3 = 0.0;
362
363 // Humification
364 day_c_humify_doc_hum_2_sl = 0.0;
365 day_c_humify_sol_hum_1_sl = 0.0;
366 day_c_humify_cel_hum_1_sl = 0.0;
367 day_c_humify_lig_hum_1_sl = 0.0;
368 day_c_humify_lig_hum_2_sl = 0.0;
369 day_c_humify_mic_hum_1_sl = 0.0;
370 day_c_humify_mic_hum_2_sl = 0.0;
371 day_c_humify_hum_1_hum_2_sl = 0.0;
372 day_c_humify_hum_2_hum_3_sl = 0.0;
373
374 // Algae
375 day_n_fix_algae = 0.0;
376 day_c_fix_algae = 0.0;
377
378 // DOC production
379 day_doc_prod_decomp_litter = 0.0;
380 day_doc_prod_decomp_humus = 0.0;
381 day_doc_prod_decomp_aorg = 0.0;
382
383 return LDNDC_ERR_OK;
384}

Referenced by MeTrX_reset().

Here is the caller graph for this function:

◆ MeTrX_reset_subdaily()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_reset_subdaily ( )
private
Parameters
[in]None
[out]None
Returns
void
214{
215 for ( int ts = 0; ts < TOTAL_TIME_STEPS; ts++)
216 {
217 subdaily_co2_bubbling[ts] = 0.0;
218 subdaily_co2_plant[ts] = 0.0;
219 subdaily_co2_soil[ts] = 0.0;
220 subdaily_co2_water[ts] = 0.0;
221 subdaily_co2_leach[ts] = 0.0;
222
223 subdaily_ch4_bubbling[ts] = 0.0;
224 subdaily_ch4_plant[ts] = 0.0;
225 subdaily_ch4_soil[ts] = 0.0;
226 subdaily_ch4_water[ts] = 0.0;
227 subdaily_ch4_leach[ts] = 0.0;
228 subdaily_ch4_prod[ts] = 0.0;
229 subdaily_ch4_ox[ts] = 0.0;
230 subdaily_acetate_prod[ts] = 0.0;
231 subdaily_doc_prod[ts] = 0.0;
232 subdaily_plant_o2_cons[ts] = 0.0;
233 subdaily_flood_o2_conc[ts] = 0.0;
234 subdaily_algae_o2_prod[ts] = 0.0;
235 subdaily_o2_bubbling[ts] = 0.0;
236 subdaily_o2_plant[ts] = 0.0;
237 subdaily_o2_soil[ts] = 0.0;
238 subdaily_o2_water[ts] = 0.0;
239 subdaily_n2o_bubbling[ts] = 0.0;
240 subdaily_n2o_plant[ts] = 0.0;
241 subdaily_n2o_soil[ts] = 0.0;
242 subdaily_n2o_water[ts] = 0.0;
243 subdaily_no_bubbling[ts] = 0.0;
244 subdaily_no_plant[ts] = 0.0;
245 subdaily_no_soil[ts] = 0.0;
246 subdaily_no_water[ts] = 0.0;
247 subdaily_nh3_bubbling[ts] = 0.0;
248 subdaily_nh3_plant[ts] = 0.0;
249 subdaily_nh3_soil[ts] = 0.0;
250 subdaily_nh3_water[ts] = 0.0;
251 subdaily_radon_soil[ts] = 0.0;
252 subdaily_radon_plant[ts] = 0.0;
253 subdaily_radon_water[ts] = 0.0;
254 }
255
256 return LDNDC_ERR_OK;
257}

Referenced by MeTrX_reset().

Here is the caller graph for this function:

◆ MeTrX_send_state()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_send_state ( )
private
Parameters
[in]None
[out]None
Returns
error code
336{
337 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
338 {
339 sc_.nh4_sl[sl] = nh4_ae_sl[sl] + nh4_an_sl[sl];
340 sc_.don_sl[sl] = don_ae_sl[sl] + don_an_sl[sl];
341 sc_.no3_sl[sl] = no3_ae_sl[sl] + no3_an_sl[sl];
342 sc_.an_no3_sl[sl] = 0.0;
343 }
344
345 return LDNDC_ERR_OK;
346}

Referenced by MeTrX_write_rates().

Here is the caller graph for this function:

◆ MeTrX_soil_organic_matter_turnover()

void ldndc::SoilChemistryMeTrX::MeTrX_soil_organic_matter_turnover ( )
private
Parameters
[in]None
[out]None
Returns
void

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_spinup()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_spinup ( )
private
Parameters
[in]None
[out]None
Returns
void
69{
70 if ( spinup_.execute_spinup( lclock()))
71 {
72 size_t sl_delta_c( 0);
73 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
74 {
75 accumulated_n_litter_spinup_sl[sl] -= sc_.n_wood_sl[sl];
76 if ( cbm::flt_greater_equal( spinup_delta_c_depth, sc_.depth_sl[sl] - 0.5 * sc_.h_sl[sl]))
77 {
78 sl_delta_c = sl;
79 }
80 }
81
82 /* WOOD */
83 double c_wood( sc_.c_wood);
84 double n_wood( sc_.n_wood);
85 if ( cbm::flt_greater_zero( spinup_.exit_wood) &&
86 cbm::flt_equal_zero( (spinup_.executed_months_+1) % 12))
87 {
88 double const fraction( 0.5);
89 double const c_wood_temp( cbm::bound( 0.5, spinup_.enter_wood / spinup_.exit_wood, 1.5) * sc_.c_wood);
90 sc_.c_wood = c_wood_temp * fraction + c_wood * (1.0 - fraction);
91
92 double const n_demand_wood( cbm::flt_greater_zero( n_wood) ?
93 sc_.c_wood / (c_wood / n_wood)
94 : 0.0);
95 sc_.n_wood = n_demand_wood;
96
97 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
98 {
99 double c_wood_sl( sc_.c_wood_sl[sl]);
100 double n_wood_sl( sc_.n_wood_sl[sl]);
101
102 double const c_wood_sl_temp( cbm::bound( 0.5, spinup_.enter_wood / spinup_.exit_wood, 1.5) * sc_.c_wood_sl[sl]);
103 sc_.c_wood_sl[sl] = c_wood_sl_temp * 0.5 + c_wood_sl * 0.5;
104
105 double const n_demand_wood_sl( cbm::flt_greater_zero( n_wood_sl) ?
106 sc_.c_wood_sl[sl] / (c_wood_sl / n_wood_sl)
107 : 0.0);
108 sc_.n_wood_sl[sl] = n_demand_wood_sl;
109 }
110 }
111
112 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
113 {
114 accumulated_n_litter_spinup_sl[sl] += sc_.n_wood_sl[sl];
115 }
116
117 /* HUMUS / AORG / LITTER */
118 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
119 {
120 int const steps( 10);
121 for ( int i = 0; i < steps; ++i)
122 {
123 double const c_hum_1( c_humus_1_sl[sl]);
124 double const n_hum_1( n_humus_1_sl[sl]);
125 double const c_hum_2( c_humus_2_sl[sl]);
126 double const n_hum_2( n_humus_2_sl[sl]);
127 double const c_hum_3( c_humus_3_sl[sl]);
128 double const n_hum_3( n_humus_3_sl[sl]);
129
130 double const c_lit_1( sc_.C_lit1_sl[sl]);
131 double const n_lit_1( sc_.N_lit1_sl[sl]);
132 double const c_lit_2( sc_.C_lit2_sl[sl]);
133 double const n_lit_2( sc_.N_lit2_sl[sl]);
134 double const c_lit_3( sc_.C_lit3_sl[sl]);
135 double const n_lit_3( sc_.N_lit3_sl[sl]);
136
137 double const c_aorg( sc_.C_aorg_sl[sl]);
138 double const n_aorg( sc_.N_aorg_sl[sl]);
139
140 double const c_lit( c_lit_1 + c_lit_2 + c_lit_3);
141 double const c_hum( c_hum_1 + c_hum_2 + c_hum_3);
142 double const c_tot( c_hum + c_lit + c_aorg);
143 double const n_lit( n_lit_1 + n_lit_2 + n_lit_3);
144 double const n_hum( n_hum_1 + n_hum_2 + n_hum_3);
145 //double const n_tot( n_hum + n_lit + n_aorg);
146
147 int spinup_steps_per_year( 12);
148 double const delta_c_hum_1( (sl <= sl_delta_c) ?
149 c_hum_1 / (c_hum_1 + c_hum_2)
150 * spinup_.decompose_hum_1[sl] / spinup_.decompose_hum_1.subvector( 0, sl_delta_c+1).sum()
151 * spinup_delta_c / spinup_steps_per_year :
152 0.0);
153 double const delta_c_hum_2( (sl <= sl_delta_c) ?
154 c_hum_2 / (c_hum_1 + c_hum_2)
155 * spinup_.decompose_hum_2[sl] / spinup_.decompose_hum_2.subvector( 0, sl_delta_c+1).sum()
156 * spinup_delta_c / spinup_steps_per_year :
157 0.0);
158 double const delta_c_hum_3( 0.0);
159
160 double const c_humus_1_tmp( cbm::bound_min( 1.0e-9,
161 spinup_.c_to_humus_1_sl[sl]
162 - delta_c_hum_1)
163 / cbm::bound_min( 1.0e-9, spinup_.decompose_hum_1[sl] + spinup_.humify_humus_1_to_humus_2_sl[sl]));
164
165 double const c_humus_2_tmp( cbm::bound_min( 1.0e-9,
166 spinup_.c_to_humus_2_sl[sl]
167 + spinup_.humify_humus_1_to_humus_2_sl[sl] * c_humus_1_sl[sl]
168 - delta_c_hum_2)
169 / cbm::bound_min( 1.0e-9, spinup_.decompose_hum_2[sl] + spinup_.humify_humus_2_to_humus_3_sl[sl]));
170
171 double const c_humus_3_tmp( cbm::bound_min( 1.0e-9,
172 spinup_.c_to_humus_3_sl[sl]
173 + spinup_.humify_humus_2_to_humus_3_sl[sl] * c_humus_2_sl[sl]
174 - delta_c_hum_3)
175 / cbm::bound_min( 1.0e-9, spinup_.decompose_hum_3[sl] + spinup_.humify_humus_2_to_humus_3_sl[sl]));
176
177 double const c_litter_1_tmp( cbm::bound_min( 1.0e-9, spinup_.c_to_lit_1[sl]) /
178 (cbm::bound_min( 1.0e-9, spinup_.loose_lit_1[sl])));
179
180 double const c_litter_2_tmp( cbm::bound_min( 1.0e-9, spinup_.c_to_lit_2[sl]) /
181 (cbm::bound_min( 1.0e-9, spinup_.loose_lit_2[sl])));
182
183 double const c_litter_3_tmp( cbm::bound_min( 1.0e-9, spinup_.c_to_lit_3[sl]) /
184 (cbm::bound_min( 1.0e-9, spinup_.loose_lit_3[sl])));
185
186 double const c_aorg_tmp( cbm::bound_min( 1.0e-9, spinup_.c_to_aorg[sl]) /
187 (cbm::bound_min( 1.0e-9, spinup_.loose_aorg[sl])));
188
189 //idea for drained peat if spinup_delta_c explicitly not used
190 if ( spinup_.spinup_type() == 1)
191 {
192 c_humus_1_sl[sl] = c_humus_1_tmp;
193 double const scale( c_hum / (c_humus_1_sl[sl] + c_humus_2_sl[sl] + c_humus_3_sl[sl]));
194 c_humus_1_sl[sl] *= scale;
195 c_humus_2_sl[sl] *= scale;
196 c_humus_3_sl[sl] *= scale;
197 }
198 else if ( spinup_.spinup_type() == 2)
199 {
200 c_humus_2_sl[sl] = c_humus_2_tmp;
201 double const scale( c_hum / (c_humus_1_sl[sl] + c_humus_2_sl[sl] + c_humus_3_sl[sl]));
202 c_humus_1_sl[sl] *= scale;
203 c_humus_2_sl[sl] *= scale;
204 c_humus_3_sl[sl] *= scale;
205 }
206 else if ( spinup_.spinup_type() == 3)
207 {
208 c_humus_3_sl[sl] = c_humus_3_tmp;
209 double const scale( c_hum / (c_humus_1_sl[sl] + c_humus_2_sl[sl] + c_humus_3_sl[sl]));
210 c_humus_1_sl[sl] *= scale;
211 c_humus_2_sl[sl] *= scale;
212 c_humus_3_sl[sl] *= scale;
213 }
214 else
215 {
216 double const fraction( 1.0 / steps);
217 if ( sl_.soil_layers_in_litter_cnt() > 0)
218 {
219 double const c_tot_tmp( c_humus_1_tmp + c_humus_2_tmp + c_humus_3_tmp +
220 c_litter_1_tmp + c_litter_2_tmp + c_litter_3_tmp + c_aorg_tmp);
221
222 sc_.C_lit1_sl[sl] = cbm::bound_max( c_litter_1_tmp * fraction + c_lit_1 * (1.0 - fraction),
223 c_litter_1_tmp / c_tot_tmp * c_tot);
224 sc_.C_lit2_sl[sl] = cbm::bound_max( c_litter_2_tmp * fraction + c_lit_2 * (1.0 - fraction),
225 c_litter_2_tmp / c_tot_tmp * c_tot);
226 sc_.C_lit3_sl[sl] = cbm::bound_max( c_litter_3_tmp * fraction + c_lit_3 * (1.0 - fraction),
227 c_litter_3_tmp / c_tot_tmp * c_tot);
228
229 sc_.C_aorg_sl[sl] = cbm::bound_max( c_aorg_tmp * fraction + c_aorg * (1.0 - fraction),
230 c_aorg_tmp / c_tot_tmp * c_tot);
231
232 double const c_litter_aorg( sc_.C_lit1_sl[sl] + sc_.C_lit2_sl[sl] + sc_.C_lit3_sl[sl] + sc_.C_aorg_sl[sl]);
233
234 //use upper limit for humus pool 1
235 c_humus_1_sl[sl] = cbm::bound_max( c_humus_1_tmp * fraction + c_hum_1 * (1.0 - fraction),
236 0.99 * c_humus_1_tmp / (c_humus_1_tmp + c_humus_2_tmp + c_humus_3_tmp)
237 * (c_tot - c_litter_aorg));
238 c_humus_2_sl[sl] = cbm::bound_max( c_humus_2_tmp * fraction + c_hum_2 * (1.0 - fraction),
239 0.99 * c_humus_2_tmp / (c_humus_2_tmp + c_humus_3_tmp)
240 * (c_tot - c_litter_aorg - c_humus_1_sl[sl]));
241 c_humus_3_sl[sl] = c_tot - c_litter_aorg - c_humus_1_sl[sl] - c_humus_2_sl[sl];
242 }
243 else
244 {
245 //use upper limit for humus pool 1
246 c_humus_1_sl[sl] = cbm::bound_max( c_humus_1_tmp * fraction + c_hum_1 * (1.0 - fraction),
247 0.99 * c_humus_1_tmp / (c_humus_1_tmp + c_humus_2_tmp + c_humus_3_tmp)
248 * c_hum);
249 c_humus_2_sl[sl] = cbm::bound_max( c_humus_2_tmp * fraction + c_hum_2 * (1.0 - fraction),
250 0.99 * c_humus_2_tmp / (c_humus_2_tmp + c_humus_3_tmp)
251 * (c_hum - c_humus_1_sl[sl]));
252 c_humus_3_sl[sl] = c_hum - c_humus_1_sl[sl] - c_humus_2_sl[sl];
253 }
254 }
255
256 if ( peat_dev)
257 {
258 double const c_maom_pot( C_SATURATION * (sc_.clay_sl[sl] + sc_.silt_sl[sl]) * sc_.get_soil_mass( sl));
259 if ( cbm::flt_greater( c_humus_2_sl[sl] + c_humus_3_sl[sl], c_maom_pot))
260 {
261 double const scale( c_maom_pot / (c_humus_2_sl[sl] + c_humus_3_sl[sl]));
262 double c_maom_to_pom( c_humus_2_sl[sl] + c_humus_3_sl[sl]);
263 c_humus_2_sl[sl] *= scale;
264 c_humus_3_sl[sl] *= scale;
265 c_maom_to_pom -= c_humus_2_sl[sl] + c_humus_3_sl[sl];
266 c_humus_1_sl[sl] += c_maom_to_pom;
267 }
268 }
269 accumulated_n_humus_1_spinup_sl[sl] -= n_humus_1_sl[sl];
270 accumulated_n_humus_2_spinup_sl[sl] -= n_humus_2_sl[sl];
271 accumulated_n_humus_3_spinup_sl[sl] -= n_humus_3_sl[sl];
272
273 n_humus_1_sl[sl] = c_humus_1_sl[sl] / cn_hum_1_sl[sl];
274 n_humus_2_sl[sl] = c_humus_2_sl[sl] / cn_hum_2_sl[sl];
275 n_humus_3_sl[sl] = c_humus_3_sl[sl] / cn_hum_3_sl[sl];
276
277 double n_tot_old( n_hum);
278 double n_tot_tmp( n_humus_1_sl[sl] + n_humus_2_sl[sl] + n_humus_3_sl[sl]);
279
280 if ( sl_.soil_layers_in_litter_cnt() > 0)
281 {
282 double const CN_MIN( 100.0);
283 double const cn_lit_1( cbm::flt_greater_zero( n_lit_1) ? c_lit_1 / n_lit_1 : CN_MIN);
284 double const cn_lit_2( cbm::flt_greater_zero( n_lit_2) ? c_lit_2 / n_lit_2 : CN_MIN);
285 double const cn_lit_3( cbm::flt_greater_zero( n_lit_3) ? c_lit_3 / n_lit_3 : CN_MIN);
286 sc_.N_lit1_sl[sl] = sc_.C_lit1_sl[sl] / cn_lit_1;
287 sc_.N_lit2_sl[sl] = sc_.C_lit2_sl[sl] / cn_lit_2;
288 sc_.N_lit3_sl[sl] = sc_.C_lit3_sl[sl] / cn_lit_3;
289
290 double const cn_aorg( cbm::flt_greater_zero( n_aorg) ? c_aorg / n_aorg : CN_MIN);
291 sc_.N_aorg_sl[sl] = sc_.C_aorg_sl[sl] / cn_aorg;
292
293 n_tot_old += n_lit + n_aorg;
294 n_tot_tmp += sc_.N_lit1_sl[sl] + sc_.N_lit2_sl[sl] + sc_.N_lit3_sl[sl] + sc_.N_aorg_sl[sl];
295 }
296
297 double const scale( n_tot_old / n_tot_tmp);
298
299 n_humus_1_sl[sl] *= scale;
300 n_humus_2_sl[sl] *= scale;
301 n_humus_3_sl[sl] *= scale;
302
303 if ( sl_.soil_layers_in_litter_cnt() > 0)
304 {
305 sc_.N_lit1_sl[sl] *= scale;
306 sc_.N_lit2_sl[sl] *= scale;
307 sc_.N_lit3_sl[sl] *= scale;
308
309 sc_.N_aorg_sl[sl] *= scale;
310 }
311
312 accumulated_n_humus_1_spinup_sl[sl] += n_humus_1_sl[sl];
313 accumulated_n_humus_2_spinup_sl[sl] += n_humus_2_sl[sl];
314 accumulated_n_humus_3_spinup_sl[sl] += n_humus_3_sl[sl];
315
316 //adapt target cn of recalcitrant pools
317 cn_hum_2_sl[sl] = c_humus_2_sl[sl] / n_humus_2_sl[sl];
318 cn_hum_3_sl[sl] = c_humus_3_sl[sl] / n_humus_3_sl[sl];
319 }
320
321 spinup_.cn_humus_2_temp_sl[sl] += cn_hum_2_sl[sl];
322 spinup_.cn_humus_3_temp_sl[sl] += cn_hum_3_sl[sl];
323
324 spinup_.c_humus_1_temp_sl[sl] += c_humus_1_sl[sl];
325 spinup_.c_humus_2_temp_sl[sl] += c_humus_2_sl[sl];
326 spinup_.c_humus_3_temp_sl[sl] += c_humus_3_sl[sl];
327
328 spinup_.c_litter_1_temp_sl[sl] += sc_.C_lit1_sl[sl];
329 spinup_.c_litter_2_temp_sl[sl] += sc_.C_lit2_sl[sl];
330 spinup_.c_litter_3_temp_sl[sl] += sc_.C_lit3_sl[sl];
331
332 spinup_.n_litter_1_temp_sl[sl] += sc_.N_lit1_sl[sl];
333 spinup_.n_litter_2_temp_sl[sl] += sc_.N_lit2_sl[sl];
334 spinup_.n_litter_3_temp_sl[sl] += sc_.N_lit3_sl[sl];
335
336 spinup_.c_aorg_temp_sl[sl] += sc_.C_aorg_sl[sl];
337 spinup_.n_aorg_temp_sl[sl] += sc_.N_aorg_sl[sl];
338 }
339
340 spinup_.executed_months_ += 1;
341
342 double const c_tot_old( c_humus_1_sl.sum() + c_humus_2_sl.sum() + c_humus_3_sl.sum() +
343 sc_.C_lit1_sl.sum() + sc_.C_lit2_sl.sum() + sc_.C_lit3_sl.sum() +
344 sc_.C_aorg_sl.sum());
345
346 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
347 {
348 double c_tot_sl( c_humus_1_sl[sl] + c_humus_2_sl[sl] + c_humus_3_sl[sl]);
349 double c_tot_temp_sl( spinup_.c_humus_1_temp_sl[sl] + spinup_.c_humus_2_temp_sl[sl] + spinup_.c_humus_3_temp_sl[sl]);
350
351 if ( sl_.soil_layers_in_litter_cnt() > 0)
352 {
353 c_tot_sl += sc_.C_lit1_sl[sl] + sc_.C_lit2_sl[sl] + sc_.C_lit3_sl[sl]
354 + sc_.C_aorg_sl[sl];
355 c_tot_temp_sl += spinup_.c_litter_1_temp_sl[sl] + spinup_.c_litter_2_temp_sl[sl] + spinup_.c_litter_3_temp_sl[sl]
356 + spinup_.c_aorg_temp_sl[sl];
357 }
358
359 double const scale_c( c_tot_sl / c_tot_temp_sl);
360
361 c_humus_1_sl[sl] = spinup_.c_humus_1_temp_sl[sl] * scale_c;
362 c_humus_2_sl[sl] = spinup_.c_humus_2_temp_sl[sl] * scale_c;
363 c_humus_3_sl[sl] = spinup_.c_humus_3_temp_sl[sl] * scale_c;
364
365 if ( sl_.soil_layers_in_litter_cnt() > 0)
366 {
367 sc_.C_lit1_sl[sl] = spinup_.c_litter_1_temp_sl[sl] * scale_c;
368 sc_.C_lit2_sl[sl] = spinup_.c_litter_2_temp_sl[sl] * scale_c;
369 sc_.C_lit3_sl[sl] = spinup_.c_litter_3_temp_sl[sl] * scale_c;
370
371 sc_.C_aorg_sl[sl] = spinup_.c_aorg_temp_sl[sl] * scale_c;
372 }
373 }
374
375 double const c_tot_new( c_humus_1_sl.sum() + c_humus_2_sl.sum() + c_humus_3_sl.sum() +
376 sc_.C_lit1_sl.sum() + sc_.C_lit2_sl.sum() + sc_.C_lit3_sl.sum() +
377 sc_.C_aorg_sl.sum());
378
379 double const c_difference( std::abs( c_tot_old - c_tot_new));
380 if ( cbm::flt_greater( c_difference, 1.0e-10))
381 {
382 KLOGERROR( name(),": C-leakage during spinup: ", c_difference*cbm::M2_IN_HA, "[kg C ha-1]");
383 }
384
385 double const n_tot_old( n_humus_1_sl.sum() + n_humus_2_sl.sum() + n_humus_3_sl.sum() +
386 + sc_.N_lit1_sl.sum() + sc_.N_lit2_sl.sum() + sc_.N_lit3_sl.sum()
387 + sc_.N_aorg_sl.sum());
388
389 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
390 {
391 cn_hum_2_sl[sl] = spinup_.cn_humus_2_temp_sl[sl] / spinup_.executed_months_;
392 cn_hum_3_sl[sl] = spinup_.cn_humus_3_temp_sl[sl] / spinup_.executed_months_;
393
394 double n_tot_sl( n_humus_1_sl[sl] + n_humus_2_sl[sl] + n_humus_3_sl[sl]);
395 double n_tot_temp_sl( c_humus_1_sl[sl] / cn_hum_1_sl[sl] +
396 c_humus_2_sl[sl] / cn_hum_2_sl[sl] +
397 c_humus_3_sl[sl] / cn_hum_3_sl[sl]);
398
399 if ( sl_.soil_layers_in_litter_cnt() > 0)
400 {
401 n_tot_sl += sc_.N_lit1_sl[sl] + sc_.N_lit2_sl[sl] + sc_.N_lit3_sl[sl]
402 + sc_.N_aorg_sl[sl];
403 n_tot_temp_sl += spinup_.n_litter_1_temp_sl[sl] / spinup_.executed_months_ +
404 spinup_.n_litter_2_temp_sl[sl] / spinup_.executed_months_ +
405 spinup_.n_litter_3_temp_sl[sl] / spinup_.executed_months_ +
406 spinup_.n_aorg_temp_sl[sl] / spinup_.executed_months_;
407 }
408
409 accumulated_n_humus_1_spinup_sl[sl] -= n_humus_1_sl[sl];
410 accumulated_n_humus_2_spinup_sl[sl] -= n_humus_2_sl[sl];
411 accumulated_n_humus_3_spinup_sl[sl] -= n_humus_3_sl[sl];
412
413 double const scale_n( n_tot_sl / n_tot_temp_sl);
414
415 n_humus_1_sl[sl] = c_humus_1_sl[sl] / cn_hum_1_sl[sl] * scale_n;
416 n_humus_2_sl[sl] = c_humus_2_sl[sl] / cn_hum_2_sl[sl] * scale_n;
417 n_humus_3_sl[sl] = c_humus_3_sl[sl] / cn_hum_3_sl[sl] * scale_n;
418
419 if ( sl_.soil_layers_in_litter_cnt() > 0)
420 {
421 sc_.N_lit1_sl[sl] = spinup_.n_litter_1_temp_sl[sl] / spinup_.executed_months_ * scale_n;
422 sc_.N_lit2_sl[sl] = spinup_.n_litter_2_temp_sl[sl] / spinup_.executed_months_ * scale_n;
423 sc_.N_lit3_sl[sl] = spinup_.n_litter_3_temp_sl[sl] / spinup_.executed_months_ * scale_n;
424
425 sc_.N_aorg_sl[sl] = spinup_.n_aorg_temp_sl[sl] / spinup_.executed_months_ * scale_n;
426 }
427
428 accumulated_n_humus_1_spinup_sl[sl] += n_humus_1_sl[sl];
429 accumulated_n_humus_2_spinup_sl[sl] += n_humus_2_sl[sl];
430 accumulated_n_humus_3_spinup_sl[sl] += n_humus_3_sl[sl];
431 }
432
433 double const n_tot_new( n_humus_1_sl.sum() + n_humus_2_sl.sum() + n_humus_3_sl.sum()
434 + sc_.N_lit1_sl.sum() + sc_.N_lit2_sl.sum() + sc_.N_lit3_sl.sum()
435 + sc_.N_aorg_sl.sum());
436
437 double const n_difference( std::abs( n_tot_old - n_tot_new));
438 if ( cbm::flt_greater( c_difference, 1.0e-10))
439 {
440 KLOGERROR( name(),": N-leakage during spinup: ", n_difference*cbm::M2_IN_HA, "[kg N ha-1]");
441 }
442
443 if ( spinup_.executed_months_ == spinup_.spinup_months())
444 {
445 spinup_.stop_spinup();
446 }
447
448 spinup_.reset();
449 }
450
451 return LDNDC_ERR_OK;
452}
static const double C_SATURATION
Definition: soilchemistry-metrx.h:34

References C_SATURATION.

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_till()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_till ( )
private
Parameters
[in]None
[out]None
Returns
error code
757{
758 if ( cbm::flt_greater( sc_.till_effect_sl[0], 1.01))
759 {
760 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
761 {
762 sc_.till_effect_sl[sl] = cbm::bound_min( 1.0, sc_.till_effect_sl[sl] * (1.0 - (sipar_.METRX_TILL_STIMULATION_2() / lclock()->time_resolution())));
763 }
764 }
765 else if ( cbm::flt_greater( sc_.till_effect_sl[0], 1.0))
766 {
767 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
768 {
769 sc_.till_effect_sl[sl] = 1.0;
770 }
771 }
772
773 EventAttributes const * ev_till = NULL;
774 while (( ev_till = m_TillEvents.pop()) != NULL)
775 {
776 /***************************/
777 /* tilling depth and layer */
778 /***************************/
779
780 double till_depth( ev_till->get( "/depth", 0.0));
781 if ( till_depth > 0.5)
782 {
783 KLOGINFO( "tilling depth greater than 0.5m, reset to 0.5m [depth=",till_depth, "m,time=",lclock_ref().to_string(),"]");
784 till_depth = 0.5;
785 }
786
787 unsigned int till_layer( SL_SURFACE_DISTRIBUTION);
788 if ( cbm::flt_greater_zero( till_depth))
789 {
790 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
791 {
792 if ( sc_.depth_sl[sl] <= till_depth)
793 {
794 sc_.till_effect_sl[sl] = sipar_.METRX_TILL_STIMULATION_1();
795 till_layer = std::max( SL_SURFACE_DISTRIBUTION, sl);
796 }
797 else { break; }
798 }
799 }
800
801 /**************************************************/
802 /* stubble, root and surface litter incorporation */
803 /**************************************************/
804
805 bool todo( true);
806 if ( todo)
807 {
808 sc_.C_lit1_sl[0] += sc_.c_stubble_lit1 + sc_.c_raw_lit_1_sl.sum();
809 sc_.C_lit2_sl[0] += sc_.c_stubble_lit2 + sc_.c_raw_lit_2_sl.sum();
810 sc_.C_lit3_sl[0] += sc_.c_stubble_lit3 + sc_.c_raw_lit_3_sl.sum();
811
812 sc_.N_lit1_sl[0] += sc_.n_stubble_lit1 + sc_.n_raw_lit_1_sl.sum();
813 sc_.N_lit2_sl[0] += sc_.n_stubble_lit2 + sc_.n_raw_lit_2_sl.sum();
814 sc_.N_lit3_sl[0] += sc_.n_stubble_lit3 + sc_.n_raw_lit_3_sl.sum();
815 }
816 else
817 {
818 sc_.c_raw_lit_1_sl[0] += sc_.c_stubble_lit1;
819 sc_.c_raw_lit_2_sl[0] += sc_.c_stubble_lit2;
820 sc_.c_raw_lit_3_sl[0] += sc_.c_stubble_lit3;
821
822 sc_.n_raw_lit_1_sl[0] += sc_.n_stubble_lit1;
823 sc_.n_raw_lit_2_sl[0] += sc_.n_stubble_lit2;
824 sc_.n_raw_lit_3_sl[0] += sc_.n_stubble_lit3;
825 }
826
827 accumulated_n_surface_litter_incorporation_via_tilling_sl[0] += sc_.n_stubble_lit1 + sc_.n_stubble_lit2 + sc_.n_stubble_lit3 ;
828 accumulated_n_litter_tilling_sl[0] += sc_.n_raw_lit_1_sl.sum() + sc_.n_raw_lit_2_sl.sum() + sc_.n_raw_lit_3_sl.sum();
829
830 sc_.c_stubble_lit1 = sc_.c_stubble_lit2 = sc_.c_stubble_lit3 = 0.0;
831 sc_.n_stubble_lit1 = sc_.n_stubble_lit2 = sc_.n_stubble_lit3 = 0.0;
832
833 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
834 {
835 accumulated_n_litter_tilling_sl[sl] -= sc_.N_lit1_sl[sl] + sc_.N_lit2_sl[sl] + sc_.N_lit3_sl[sl] + sc_.n_raw_lit_1_sl[sl] + sc_.n_raw_lit_2_sl[sl] + sc_.n_raw_lit_3_sl[sl];
836 accumulated_n_aorg_tilling_sl[sl] -= sc_.N_aorg_sl[sl];
837 accumulated_n_humus_1_tilling_sl[sl] -= n_humus_1_sl[sl];
838 accumulated_n_humus_2_tilling_sl[sl] -= n_humus_2_sl[sl];
839 accumulated_n_humus_3_tilling_sl[sl] -= n_humus_3_sl[sl];
840 accumulated_n_no3_tilling_sl[sl] -= no3_ae_sl[sl] + no3_an_sl[sl];
841 accumulated_n_no2_tilling_sl[sl] -= sc_.no2_sl[sl] + sc_.an_no2_sl[sl];
842 accumulated_n_no_tilling_sl[sl] -= no_gas_sl[sl] + no_liq_sl[sl] + an_no_gas_sl[sl] + an_no_liq_sl[sl];
843 accumulated_n_n2o_tilling_sl[sl] -= n2o_gas_sl[sl] + n2o_liq_sl[sl] + an_n2o_gas_sl[sl] + an_n2o_liq_sl[sl];
844 accumulated_n_urea_tilling_sl[sl] -= sc_.urea_sl[sl];
845 accumulated_n_don_tilling_sl[sl] -= don_ae_sl[sl] + don_an_sl[sl];
846 accumulated_n_nh4_tilling_sl[sl] -= nh4_ae_sl[sl] + nh4_an_sl[sl] + sc_.clay_nh4_sl[sl];
847 accumulated_n_nh3_tilling_sl[sl] -= sc_.nh3_gas_sl[sl] + sc_.nh3_liq_sl[sl];
848 accumulated_n_microbes_tilling_sl[sl] -= n_micro_1_sl[sl] + n_micro_2_sl[sl] + n_micro_3_sl[sl];
849 }
850
851 if ( todo)
852 {
853 sc_.c_raw_lit_1_sl = sc_.c_raw_lit_2_sl = sc_.c_raw_lit_3_sl = 0.0;
854 sc_.n_raw_lit_1_sl = sc_.n_raw_lit_2_sl = sc_.n_raw_lit_3_sl = 0.0;
855 }
856
857 /****************************************/
858 /* rearranging soil pools after tilling */
859 /****************************************/
860
861 lvector_t< double > pool_buf[] =
862 {
863 sc_.fe2_sl, sc_.fe3_sl,
864 sc_.c_raw_lit_1_sl, sc_.c_raw_lit_2_sl, sc_.c_raw_lit_3_sl,
865 sc_.n_raw_lit_1_sl, sc_.n_raw_lit_2_sl, sc_.n_raw_lit_3_sl,
866 sc_.C_lit1_sl, sc_.C_lit2_sl, sc_.C_lit3_sl,
867 sc_.N_lit1_sl, sc_.N_lit2_sl, sc_.N_lit3_sl,
868 sc_.C_aorg_sl, sc_.N_aorg_sl,
869 sc_.C_micro1_sl, sc_.C_micro2_sl, sc_.C_micro3_sl,
870 n_micro_1_sl, n_micro_2_sl, n_micro_3_sl,
871 c_humus_1_sl, c_humus_2_sl, c_humus_3_sl,
872 n_humus_1_sl, n_humus_2_sl, n_humus_3_sl,
873 sc_.doc_sl, sc_.an_doc_sl,
874 ae_acetate_sl, an_acetate_sl,
875 no3_ae_sl, no3_an_sl,
876 sc_.no2_sl, sc_.an_no2_sl,
877 don_ae_sl, don_an_sl,
878 nh4_ae_sl, nh4_an_sl, sc_.clay_nh4_sl,
879 sc_.urea_sl, sc_.nh3_gas_sl, sc_.nh3_liq_sl,
880 no_gas_sl, no_liq_sl, an_no_gas_sl, an_no_liq_sl,
881 n2o_gas_sl, n2o_liq_sl, an_n2o_gas_sl, an_n2o_liq_sl
882 };
883
884 size_t const pools_cnt( sizeof( pool_buf) / sizeof(lvector_t< double >));
885 for ( size_t k = 0; k < pools_cnt; ++k)
886 {
887 // summing up pool down to tilling depth
888 double pool_sum( pool_buf[k].sum( till_layer) / sc_.depth_sl[till_layer-1]);
889 for ( size_t l = 0; l < till_layer; l++)
890 {
891 pool_buf[k][l] = pool_sum * sc_.h_sl[l];
892 }
893 }
894
895 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
896 {
897 accumulated_n_litter_tilling_sl[sl] += sc_.N_lit1_sl[sl] + sc_.N_lit2_sl[sl] + sc_.N_lit3_sl[sl] + sc_.n_raw_lit_1_sl[sl] + sc_.n_raw_lit_2_sl[sl] + sc_.n_raw_lit_3_sl[sl];
898 accumulated_n_aorg_tilling_sl[sl] += sc_.N_aorg_sl[sl];
899 accumulated_n_humus_1_tilling_sl[sl] += n_humus_1_sl[sl];
900 accumulated_n_humus_2_tilling_sl[sl] += n_humus_2_sl[sl];
901 accumulated_n_humus_3_tilling_sl[sl] += n_humus_3_sl[sl];
902 accumulated_n_no3_tilling_sl[sl] += no3_ae_sl[sl] + no3_an_sl[sl];
903 accumulated_n_no2_tilling_sl[sl] += sc_.no2_sl[sl] + sc_.an_no2_sl[sl];
904 accumulated_n_no_tilling_sl[sl] += no_gas_sl[sl] + no_liq_sl[sl] + an_no_gas_sl[sl] + an_no_liq_sl[sl];
905 accumulated_n_n2o_tilling_sl[sl] += n2o_gas_sl[sl] + n2o_liq_sl[sl] + an_n2o_gas_sl[sl] + an_n2o_liq_sl[sl];
906 accumulated_n_urea_tilling_sl[sl] += sc_.urea_sl[sl];
907 accumulated_n_don_tilling_sl[sl] += don_ae_sl[sl] + don_an_sl[sl];
908 accumulated_n_nh4_tilling_sl[sl] += nh4_ae_sl[sl] + nh4_an_sl[sl] + sc_.clay_nh4_sl[sl];
909 accumulated_n_nh3_tilling_sl[sl] += sc_.nh3_gas_sl[sl] + sc_.nh3_liq_sl[sl];
910 accumulated_n_microbes_tilling_sl[sl] += n_micro_1_sl[sl] + n_micro_2_sl[sl] + n_micro_3_sl[sl];
911 }
912 }
913
914 return LDNDC_ERR_OK;
915}

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_update()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_update ( )
private
Parameters
[in]None
[out]None
Returns
error code
63{
64 lerr_t rc = MeTrX_receive_state();
65 if ( rc)
66 {
67 return LDNDC_ERR_FAIL;
68 }
69
70 /* vertical discretization */
72
73 /* module specific variables from global state */
74 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
75 {
76 /* use liq/gas distribution from previous time step */
77 UPDATE_STATE( no_liq_sl[sl], no_gas_sl[sl], sc_.no_sl[sl]);
78 UPDATE_STATE( an_no_liq_sl[sl], an_no_gas_sl[sl], sc_.an_no_sl[sl]);
79 UPDATE_STATE( n2o_liq_sl[sl], n2o_gas_sl[sl], sc_.n2o_sl[sl]);
80 UPDATE_STATE( an_n2o_liq_sl[sl], an_n2o_gas_sl[sl], sc_.an_n2o_sl[sl]);
81
82 CHECK_FOR_ZERO( sc_.C_lit1_sl[sl]);
83 CHECK_FOR_ZERO( sc_.C_lit2_sl[sl]);
84 CHECK_FOR_ZERO( sc_.C_lit3_sl[sl]);
85 CHECK_FOR_ZERO( sc_.N_lit1_sl[sl]);
86 CHECK_FOR_ZERO( sc_.N_lit2_sl[sl]);
87 CHECK_FOR_ZERO( sc_.N_lit3_sl[sl]);
88 }
89
90 /* water table */
91 if ( cbm::flt_greater( wc_.surface_water, 0.01) &&
92 (sb_.surfacebulk_layer_cnt() > 0))
93 {
94 have_water_table = true;
95
96 // for simplicity of calculations changing watertable
97 // alters heigth of single waterlayer and not number of layers
98 h_wl = (wc_.surface_water / (double)sb_.surfacebulk_layer_cnt());
99 }
100 else if ( !cbm::flt_greater( wc_.surface_ice, 0.0))
101 {
102 have_water_table = false;
103 h_wl = 0.0;
104
105 double const clear_ch4( sb_.ch4_sbl.sum());
106 sb_.ch4_sbl = 0.0;
107 double const clear_o2( sb_.o2_sbl.sum());
108 sb_.o2_sbl = 0.0;
109 double const clear_nh4( sb_.nh4_sbl.sum());
110 sb_.nh4_sbl = 0.0;
111 double const clear_nh3( sb_.nh3_sbl.sum());
112 sb_.nh3_sbl = 0.0;
113 double const clear_urea( sb_.urea_sbl.sum());
114 sb_.urea_sbl = 0.0;
115 double const clear_no3( sb_.no3_sbl.sum());
116 sb_.no3_sbl = 0.0;
117 double const clear_don( sb_.don_sbl.sum());
118 sb_.don_sbl = 0.0;
119 double const clear_doc( sb_.doc_sbl.sum());
120 sb_.doc_sbl = 0.0;
121 double const clear_co2( sb_.co2_sbl.sum());
122 sb_.co2_sbl = 0.0;
123 double const clear_so4( sb_.so4_sbl.sum());
124 sb_.so4_sbl = 0.0;
125
126 for( size_t sl = 0; sl <= SL_SURFACE_DISTRIBUTION; ++sl)
127 {
128 ch4_liq_sl[sl] += clear_ch4 * SL_SURFACE_DISTRIBUTION_INVERSE;
129 o2_liq_sl[sl] += clear_o2 * SL_SURFACE_DISTRIBUTION_INVERSE;
130 nh4_ae_sl[sl] += clear_nh4 * SL_SURFACE_DISTRIBUTION_INVERSE;
131 sc_.nh3_liq_sl[sl] += clear_nh3 * SL_SURFACE_DISTRIBUTION_INVERSE;
132 sc_.urea_sl[sl] += clear_urea * SL_SURFACE_DISTRIBUTION_INVERSE;
133 no3_ae_sl[sl] += clear_no3 * SL_SURFACE_DISTRIBUTION_INVERSE;
134 don_ae_sl[sl] += clear_don * SL_SURFACE_DISTRIBUTION_INVERSE;
135 sc_.doc_sl[sl] += clear_doc * SL_SURFACE_DISTRIBUTION_INVERSE;
136 co2_liq_sl[sl] += clear_co2 * SL_SURFACE_DISTRIBUTION_INVERSE;
137 sc_.so4_sl[sl] += clear_so4 * SL_SURFACE_DISTRIBUTION_INVERSE;
138
139 accumulated_n_nh4_infiltration_phys_sl[sl] += clear_nh4 * SL_SURFACE_DISTRIBUTION_INVERSE;
140 accumulated_n_nh3_infiltration_phys_sl[sl] += clear_nh3 * SL_SURFACE_DISTRIBUTION_INVERSE;
141 accumulated_n_urea_infiltration_phys_sl[sl] += clear_urea * SL_SURFACE_DISTRIBUTION_INVERSE;
142 accumulated_n_no3_infiltration_phys_sl[sl] += clear_no3 * SL_SURFACE_DISTRIBUTION_INVERSE;
143 accumulated_n_don_infiltration_phys_sl[sl] += clear_don * SL_SURFACE_DISTRIBUTION_INVERSE;
144 }
145 }
146
147 /* water fluxes */
148 infiltration = wc_.accumulated_infiltration - accumulated_infiltration_old;
149 accumulated_infiltration_old = wc_.accumulated_infiltration;
150 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
151 {
152 waterflux_sl[sl] = wc_.accumulated_waterflux_sl[sl] - accumulated_waterflux_old_sl[sl];
153 accumulated_waterflux_old_sl[sl] = wc_.accumulated_waterflux_sl[sl];
154 }
155
156 /* nitrogen deposition */
157 if ( cbm::flt_greater_zero( wc_.surface_water) || cbm::flt_greater_zero( wc_.surface_ice))
158 {
159 accumulated_n_nh4_throughfall_sbl[0] += ph_.accumulated_nh4_throughfall - accumulated_n_nh4_throughfall_old;
160 accumulated_n_no3_throughfall_sbl[0] += ph_.accumulated_no3_throughfall - accumulated_n_no3_throughfall_old;
161 }
162 else
163 {
164 accumulated_n_nh4_throughfall_sl[0] += ph_.accumulated_nh4_throughfall - accumulated_n_nh4_throughfall_old;
165 accumulated_n_no3_throughfall_sl[0] += ph_.accumulated_no3_throughfall - accumulated_n_no3_throughfall_old;
166 }
167 accumulated_n_nh4_throughfall_old = ph_.accumulated_nh4_throughfall;
168 accumulated_n_no3_throughfall_old = ph_.accumulated_no3_throughfall;
169
170 /* carbon/nitrogen flux planting */
171 EventAttributes const * ev_plant = NULL;
172 while (( ev_plant = this->m_PlantEvents.pop()) != NULL)
173 {
174 MoBiLE_Plant *p = m_veg->get_plant( ev_plant->get( "/name", "?"));
175 if ( p)
176 {
177 accumulated_n_to_living_plant_and_algae_from_extern_sl[0] += p->total_nitrogen();
178
179 if ( spinup_.spinup_stage( this->lclock()))
180 {
181 site::input_class_site_t const *s_site( io_kcomm->get_input_class< site::input_class_site_t >());
182 ldndc::wood_initialization(sl_, p, sc_, s_site->soil_use_history());
183 }
184 }
185 }
186
187 /* carbon/nitrogen flux harvest/cutting */
188 accumulated_n_export_harvest_cutting_grazing += ph_.accumulated_n_export_harvest - accumulated_n_export_harvest_old;
189 accumulated_n_export_harvest_old = ph_.accumulated_n_export_harvest;
190
191 /* carbon/nitrogen flux litterfall */
192 if ( spinup_.spinup_stage( this->lclock()))
193 {
194 double const delta_c_wood( sc_.accumulated_c_litter_wood_above - accumulated_c_litter_wood_above_old);
195 if ( cbm::flt_greater_zero( delta_c_wood))
196 {
197 spinup_.enter_wood += delta_c_wood;
198 }
199 }
200 accumulated_c_litter_wood_above_old = sc_.accumulated_c_litter_wood_above;
201 accumulated_n_litter_from_plants_above_wood = sc_.accumulated_n_litter_wood_above;
202 accumulated_n_litter_from_plants_above_rawlitter = sc_.accumulated_n_litter_above;
203 accumulated_n_litter_from_plants_above_stubble = sc_.accumulated_n_litter_stubble;
204 for ( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
205 {
206 accumulated_n_litter_from_plants_below_rawlitter_sl[sl] = sc_.accumulated_n_litter_below_sl[sl];
207 accumulated_n_litter_from_plants_below_wood_sl[sl] = sc_.accumulated_n_litter_wood_below_sl[sl];
208 }
209
210 /* carbon/nitrogen flux root exsudation */
211 double const delta_c_exsudation( sc_.accumulated_c_root_exsudates_sl.sum() -
212 accumulated_c_root_exsudates_old_sl.sum());
213 if ( cbm::flt_greater_zero( delta_c_exsudation))
214 {
215 dC_root_exsudates += delta_c_exsudation;
216 subdaily_doc_prod[subdaily_time_step_] += delta_c_exsudation;
217 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
218 {
219 double const delta_c_exsudation_sl( sc_.accumulated_c_root_exsudates_sl[sl] - accumulated_c_root_exsudates_old_sl[sl]);
220 day_doc_prod_sl[sl] += delta_c_exsudation_sl;
221 accumulated_c_root_exsudates_old_sl[sl] = sc_.accumulated_c_root_exsudates_sl[sl];
222 }
223 }
224
225 /* litter layer characterization */
226 double bio_coniferous( 0.0);
227 double bio_deciduous( 0.0);
228 for ( PlantIterator vt = this->m_veg->begin(); vt != this->m_veg->end(); ++vt)
229 {
230 MoBiLE_Plant *p( *vt);
231 if ( (*p)->DECIDUOUS())
232 {
233 bio_deciduous += p->aboveground_biomass();
234 }
235 else
236 {
237 bio_coniferous += p->aboveground_biomass();
238 }
239 }
240 double const bio_tot( bio_deciduous + bio_coniferous);
241 if ( cbm::flt_greater_zero( bio_tot))
242 {
243 double const frac_deciduous( bio_deciduous / bio_tot);
244 double const frac_coniferous( 1.0 - frac_deciduous);
245 for (size_t sl = 0; sl <= SL_SURFACE_DISTRIBUTION; ++sl)
246 {
247 litter_type_fact_sl[sl] = (frac_deciduous + sipar_.METRX_KR_REDUCTION_CONIFEROUS() * frac_coniferous);
248 }
249 }
250
251 return LDNDC_ERR_OK;
252}
lerr_t MeTrX_update_soil_discretization(bool)
Definition: soilchemistry-metrx-reset.cpp:19
lerr_t MeTrX_receive_state()
Definition: soilchemistry-metrx-communicate.cpp:260
lerr_t wood_initialization(soillayers::input_class_soillayers_t const &, MoBiLE_Plant *, substate_soilchemistry_t &, ecosystem_type_e)
Initialization of aboveground and belowground wood debris, derived from existing vegetation.
Definition: ld_wood_initialization.cpp:18

References MeTrX_receive_state(), MeTrX_update_soil_discretization(), and ldndc::wood_initialization().

Referenced by solve().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ MeTrX_update_soil_discretization()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_update_soil_discretization ( bool  _update_litter)
private
Parameters
[in]None
[out]None
Returns
error code
20{
21 if ( _update_litter && (sl_.soil_layers_in_litter_cnt() > 0))
22 {
23 double const raw_litter_above( sc_.c_raw_lit_1_above +
24 sc_.c_raw_lit_2_above +
25 sc_.c_raw_lit_3_above);
26
27 double * h_litter_neq_sl = new double[sl_.soil_layers_in_litter_cnt()];
28 double h_litter_tot( 0.0);
29 double volume_water_tot( 0.0);
30 double volume_ice_tot( 0.0);
31 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
32 {
33 if ( sl < sl_.soil_layers_in_litter_cnt())
34 {
35 if ( cbm::flt_greater_zero( sc_.dens_sl[sl] * sc_.fcorg_sl[sl]) &&
36 cbm::flt_greater_zero( sc_.som_sl[sl]))
37 {
38 double const volume_water( wc_.wc_sl[sl] * sc_.h_sl[sl]);
39 volume_water_tot += volume_water;
40
41 double const volume_ice( wc_.ice_sl[sl] * sc_.h_sl[sl]);
42 volume_ice_tot += volume_ice;
43
44 double const mass_soil( sc_.min_sl[sl] + sc_.som_sl[sl] + raw_litter_above
45 / sl_.soil_layers_in_litter_cnt());
46 double const density_soil( cbm::DM3_IN_M3 * sc_.dens_sl[sl]);
47
48 h_litter_neq_sl[sl] = mass_soil / density_soil;
49 h_litter_tot += mass_soil / density_soil;
50 }
51 }
52 }
53 double h_litter_eq_sl( h_litter_tot / sl_.soil_layers_in_litter_cnt());
54
55 // Create a list of pool arrays (all same size)
56 std::vector<lvector_t<double>*> pools = {
57 &c_humus_1_sl,
58 &c_humus_2_sl,
59 &c_humus_3_sl,
60 &n_humus_1_sl,
61 &n_humus_2_sl,
62 &n_humus_3_sl,
63 &sc_.c_wood_sl,
64 &sc_.n_wood_sl,
65 &sc_.c_raw_lit_1_sl,
66 &sc_.c_raw_lit_2_sl,
67 &sc_.c_raw_lit_3_sl,
68 &sc_.n_raw_lit_1_sl,
69 &sc_.n_raw_lit_2_sl,
70 &sc_.n_raw_lit_3_sl,
71 &sc_.C_lit1_sl,
72 &sc_.C_lit2_sl,
73 &sc_.C_lit3_sl,
74 &sc_.N_lit1_sl,
75 &sc_.N_lit2_sl,
76 &sc_.N_lit3_sl,
77 &sc_.C_aorg_sl,
78 &sc_.N_aorg_sl
79 };
80
81 std::vector<double> distribute_total( pools.size(), 0.0);
82
83 size_t n = sl_.soil_layers_in_litter_cnt();
84
85 for ( size_t sl = 0; sl < n; ++sl)
86 {
87 if ( h_litter_neq_sl[sl] > h_litter_eq_sl)
88 {
89 double fraction = 1.0 - h_litter_eq_sl / h_litter_neq_sl[sl];
90
91 for (size_t p = 0; p < pools.size(); ++p)
92 {
93 double value_sl = (*pools[p])[sl];
94 double distribute_sl = fraction * value_sl;
95
96 (*pools[p])[sl] -= distribute_sl;
97 distribute_total[p] += distribute_sl;
98 }
99 }
100 }
101
102 for ( size_t sl = 0; sl < n; ++sl)
103 {
104 if ( h_litter_neq_sl[sl] < h_litter_eq_sl)
105 {
106 double fraction = h_litter_eq_sl / h_litter_neq_sl[sl] - 1.0;
107
108 for ( size_t p = 0; p < pools.size(); ++p)
109 {
110 double value_sl = (*pools[p])[sl];
111 double need_sl = fraction * value_sl;
112
113 // Limit by remaining pool-level supply
114 double distribute_sl = cbm::bound_max(need_sl, distribute_total[p]);
115
116 (*pools[p])[sl] += distribute_sl;
117 distribute_total[p] -= distribute_sl;
118 }
119 }
120 }
121
122 for ( size_t p = 0; p < pools.size(); ++p)
123 {
124 if ( cbm::flt_greater_zero( distribute_total[p]))
125 {
126 for ( size_t sl = 0; sl < n; ++sl)
127 {
128 (*pools[p])[sl] += distribute_total[p] / n;
129 }
130 distribute_total[p] = 0.0;
131 }
132 }
133
134 double h_cum( 0.0);
135 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
136 {
137 if ( sl < sl_.soil_layers_in_litter_cnt())
138 {
139 sc_.h_sl[sl] = h_litter_eq_sl;
140
141 double pore_vol_avail( 0.99 * sc_.poro_sl[sl] * sc_.h_sl[sl]);
142 double const ice_vol( (1.0 / sl_.soil_layers_in_litter_cnt() * volume_ice_tot));
143 if ( cbm::flt_greater( ice_vol, pore_vol_avail))
144 {
145 wc_.surface_ice += ice_vol - pore_vol_avail;
146 wc_.ice_sl[sl] = pore_vol_avail / sc_.h_sl[sl];
147 }
148 else
149 {
150 wc_.ice_sl[sl] = ice_vol / sc_.h_sl[sl];
151 }
152
153 pore_vol_avail = cbm::bound_min( 0.0, 0.99 * sc_.poro_sl[sl] * sc_.h_sl[sl] - ice_vol);
154 double const water_vol( (1.0 / sl_.soil_layers_in_litter_cnt() * volume_water_tot));
155 if ( cbm::flt_greater( water_vol, pore_vol_avail))
156 {
157 wc_.surface_water += water_vol - pore_vol_avail;
158 wc_.wc_sl[sl] = pore_vol_avail / sc_.h_sl[sl];
159 }
160 else
161 {
162 wc_.wc_sl[sl] = water_vol / sc_.h_sl[sl];
163 }
164 }
165 h_cum += sc_.h_sl[sl];
166 sc_.depth_sl[sl] = h_cum;
167 }
168 }
169
170 for( size_t sl = 0; sl < sl_.soil_layer_cnt()-1; ++sl)
171 {
172 delta_x[sl] = cbm::arithmetic_mean2( sc_.h_sl[sl], sc_.h_sl[sl+1]);
173 }
174 delta_x[sl_.soil_layer_cnt()-1] = sc_.h_sl[sl_.soil_layer_cnt()-1];
175
176 return LDNDC_ERR_OK;
177}

Referenced by MeTrX_update().

Here is the caller graph for this function:

◆ MeTrX_urea_hydrolysis()

void ldndc::SoilChemistryMeTrX::MeTrX_urea_hydrolysis ( )
private
Parameters
[in]None
[out]None
Returns
void
934{
935 if ( have_water_table)
936 {
937 double urea_hydrolysis_sum( 0.0);
938 for ( size_t wl = 0; wl < sb_.surfacebulk_layer_cnt(); ++wl)
939 {
940 if ( cbm::flt_greater_zero( sb_.urea_sbl[wl]))
941 {
942 crnf_.update_urease_inhibition( mc_temp_sl[0] * FTS_TOT_, sb_.ui_sbl.sum(), sb_.ui_sbl[wl]);
943 double const fact_t( std::exp( -sipar_.METRX_F_DECOMP_T_EXP_1() * pow(1.0 - mc_temp_sl[0] / sipar_.METRX_F_DECOMP_T_EXP_2(), 2.0)));
944 double const urease_inhibition( crnf_.get_urease_inhibition( sb_.ui_sbl[wl]));
945 double const k_mm( cbm::flt_greater_zero( urease_inhibition) ?
946 (sipar_.METRX_KMM_UREA_HYDROLYSIS() +
947 urease_inhibition * sipar_.METRX_KMM_UREA_HYDROLYSIS_INHIBITION()) * h_wl :
948 sipar_.METRX_KMM_UREA_HYDROLYSIS() * h_wl);
949 double const fact_urea( sb_.urea_sbl[wl] / (sb_.urea_sbl[wl] + k_mm));
950 double const urea_hydrolysis( cbm::bound_max( sipar_.METRX_KR_UREA_HYDROLYSIS() * fact_urea * fact_t * sb_.urea_sbl[wl] * FTS_TOT_,
951 0.99 * sb_.urea_sbl[wl]));
952
953 sb_.urea_sbl[wl] -= urea_hydrolysis;
954 sb_.nh4_sbl[wl] += urea_hydrolysis;
955 accumulated_n_urea_nh4_hydrolysis_sbl[0] += urea_hydrolysis;
956 urea_hydrolysis_sum += urea_hydrolysis;
957 }
958 else
959 {
960 sb_.urea_sbl[wl] = 0.0;
961 }
962 }
963 ph_delta_urea_wl = cbm::bound( 0.0, urea_hydrolysis_sum / (sipar_.METRX_KMM_PH_INCREASE_FROM_UREA() * wc_.surface_water), PH_MAX-PH_SURFACE_WATER);
964 }
965
966 for ( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
967 {
968 if ( cbm::flt_greater_zero( sc_.urea_sl[sl]))
969 {
970 crnf_.update_urease_inhibition( mc_temp_sl[sl] * FTS_TOT_, sc_.ui_sl.sum(), sc_.ui_sl[sl]);
971 double const fact_t( std::exp( -sipar_.METRX_F_DECOMP_T_EXP_1() * pow(1.0 - mc_temp_sl[sl] / sipar_.METRX_F_DECOMP_T_EXP_2(), 2.0)));
972 double const urease_inhibition( crnf_.get_urease_inhibition( sc_.ui_sl[sl]));
973 double const k_mm( cbm::flt_greater_zero( urease_inhibition) ?
974 (sipar_.METRX_KMM_UREA_HYDROLYSIS() +
975 urease_inhibition * sipar_.METRX_KMM_UREA_HYDROLYSIS_INHIBITION()) * sc_.h_sl[sl] :
976 sipar_.METRX_KMM_UREA_HYDROLYSIS() * sc_.h_sl[sl]);
977 double const fact_urea( sc_.urea_sl[sl] / (sc_.urea_sl[sl] + k_mm));
978 double const urea_hydrolysis( cbm::bound_max( sipar_.METRX_KR_UREA_HYDROLYSIS() * fact_urea * fact_t * sc_.urea_sl[sl] * FTS_TOT_, 0.99 * sc_.urea_sl[sl]));
979
980 sc_.urea_sl[sl] -= urea_hydrolysis;
981 nh4_ae_sl[sl] += urea_hydrolysis * (1.0 - sc_.anvf_sl[sl]);
982 nh4_an_sl[sl] += urea_hydrolysis * sc_.anvf_sl[sl];
983 accumulated_n_urea_nh4_hydrolysis_sl[sl] += urea_hydrolysis;
984 ph_delta_urea_sl[sl] = cbm::bound( 0.0, urea_hydrolysis / (sipar_.METRX_KMM_PH_INCREASE_FROM_UREA() * sc_.h_sl[sl]), PH_MAX-sc_.phi_sl[sl]);
985 }
986 else
987 {
988 sc_.urea_sl[sl] = 0.0;
989 ph_delta_urea_sl[sl] = 0.0;
990 }
991 }
992}

Referenced by solve().

Here is the caller graph for this function:

◆ MeTrX_write_output()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_write_output ( )
private
Parameters
[in]None
[out]None
Returns
error code
17{
18 if ( !output_data_ || !this->output_writer_.active())
19 {
20 return LDNDC_ERR_OK;
21 }
22
23 if ( output_writer_.write_subdaily())
24 {
25 lerr_t rc_out = MeTrX_write_output_subdaily();
26 if ( rc_out){ return LDNDC_ERR_FAIL; }
27 }
28
29 if ( output_writer_.write_fluxes())
30 {
31 lerr_t rc_out = MeTrX_write_output_fluxes();
32 if ( rc_out){ return LDNDC_ERR_FAIL; }
33 }
34
35 if ( lclock()->is_position( TMODE_POST_DAILY))
36 {
37 if ( output_writer_.write_pools())
38 {
39 lerr_t rc_out = MeTrX_write_output_pools();
40 if ( rc_out){ return LDNDC_ERR_FAIL; }
41 }
42
43 if ( output_writer_.write_daily())
44 {
45 lerr_t rc_out = MeTrX_write_output_daily();
46 if ( rc_out){ return LDNDC_ERR_FAIL; }
47 }
48
49 if ( output_writer_.write_layer_daily())
50 {
51 lerr_t rc_out = MeTrX_write_output_layer_daily();
52 if ( rc_out){ return LDNDC_ERR_FAIL; }
53 }
54 }
55
56 if ( lclock()->is_position( TMODE_POST_YEARLY))
57 {
58 if ( output_writer_.write_yearly())
59 {
60 lerr_t rc_out = MeTrX_write_output_yearly();
61 if ( rc_out){ return LDNDC_ERR_FAIL; }
62 }
63
64 if ( output_writer_.write_layer_yearly())
65 {
66 lerr_t rc_out = MeTrX_write_output_layer_yearly();
67 if ( rc_out){ return LDNDC_ERR_FAIL; }
68 }
69 }
70
71 return LDNDC_ERR_OK;
72}
lerr_t MeTrX_write_output_fluxes()
Definition: soilchemistry-metrx-output.cpp:725
lerr_t MeTrX_write_output_layer_yearly()
Definition: soilchemistry-metrx-output.cpp:629
lerr_t MeTrX_write_output_yearly()
Definition: soilchemistry-metrx-output.cpp:409
lerr_t MeTrX_write_output_layer_daily()
Definition: soilchemistry-metrx-output.cpp:453
lerr_t MeTrX_write_output_daily()
Definition: soilchemistry-metrx-output.cpp:76
lerr_t MeTrX_write_output_subdaily()
Definition: soilchemistry-metrx-output.cpp:971
lerr_t MeTrX_write_output_pools()
Definition: soilchemistry-metrx-output.cpp:656

References MeTrX_write_output_daily(), MeTrX_write_output_fluxes(), MeTrX_write_output_layer_daily(), MeTrX_write_output_layer_yearly(), MeTrX_write_output_pools(), MeTrX_write_output_subdaily(), and MeTrX_write_output_yearly().

Referenced by solve().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ MeTrX_write_output_daily()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_write_output_daily ( )
private
Parameters
[in]None
[out]None
Returns
error code
77{
78#define METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT(__val__) LDNDC_OUTPUT_SET_COLUMN_((__val__),=,output_data_,1)
79 LDNDC_OUTPUT_SET_COLUMN_INDEX(0);
80
81 double const c_stub( sc_.c_stubble_lit1 + sc_.c_stubble_lit2 + sc_.c_stubble_lit3);
82 double const n_stub( sc_.n_stubble_lit1 + sc_.n_stubble_lit2 + sc_.n_stubble_lit3);
83
84 double const c_litter_above( sc_.c_raw_lit_1_above + sc_.c_raw_lit_2_above + sc_.c_raw_lit_3_above);
85 double const n_litter_above( sc_.n_raw_lit_1_above + sc_.n_raw_lit_2_above + sc_.n_raw_lit_3_above);
86
87 double const c_litter_soil_1( sc_.C_lit1_sl.sum() + sc_.c_raw_lit_1_sl.sum());
88 double const c_litter_soil_2( sc_.C_lit2_sl.sum() + sc_.c_raw_lit_2_sl.sum());
89 double const c_litter_soil_3( sc_.C_lit3_sl.sum() + sc_.c_raw_lit_3_sl.sum());
90 double const n_litter_soil_1( sc_.N_lit1_sl.sum() + sc_.n_raw_lit_1_sl.sum());
91 double const n_litter_soil_2( sc_.N_lit2_sl.sum() + sc_.n_raw_lit_2_sl.sum());
92 double const n_litter_soil_3( sc_.N_lit3_sl.sum() + sc_.n_raw_lit_3_sl.sum());
93
94 double const c_mic_1( sc_.C_micro1_sl.sum());
95 double const c_mic_2( sc_.C_micro2_sl.sum());
96 double const c_mic_3( sc_.C_micro3_sl.sum());
97 double const n_mic_1( n_micro_1_sl.sum());
98 double const n_mic_2( n_micro_2_sl.sum());
99 double const n_mic_3( n_micro_3_sl.sum());
100
101 double const c_hum_1( c_humus_1_sl.sum());
102 double const c_hum_2( c_humus_2_sl.sum());
103 double const c_hum_3( c_humus_3_sl.sum());
104 double const n_hum_1( n_humus_1_sl.sum());
105 double const n_hum_2( n_humus_2_sl.sum());
106 double const n_hum_3( n_humus_3_sl.sum());
107
108 double const c_aorg( sc_.C_aorg_sl.sum());
109 double const n_aorg( sc_.N_aorg_sl.sum());
110
111 double const c_wood( sc_.c_wood_sl.sum() + sc_.c_wood);
112 double const n_wood( sc_.n_wood_sl.sum() + sc_.n_wood);
113
114 double const n_algae_tot( n_algae + n_dead_algae);
115 double const don_sum( don_ae_sl.sum()+don_an_sl.sum()+sb_.don_sbl.sum());
116 double const nh4_sum( nh4_ae_sl.sum()+nh4_an_sl.sum()+sb_.nh4_sbl.sum());
117 double const nh4_clay_sum( sc_.clay_nh4_sl.sum());
118 double const coated_nh4_sum( sc_.coated_nh4_sl.sum());
119 double const urea_sum( sc_.urea_sl.sum()+sb_.urea_sbl.sum());
120 double const no2_sum( sc_.no2_sl.sum());
121 double const an_no2_sum( sc_.an_no2_sl.sum());
122 double const no3_sum( no3_ae_sl.sum());
123 double const an_no3_sum( no3_an_sl.sum()+sb_.no3_sbl.sum());
124 double const n2o_sum( n2o_gas_sl.sum()+n2o_liq_sl.sum());
125 double const an_n2o_sum( an_n2o_gas_sl.sum()+an_n2o_liq_sl.sum());
126 double const no_sum( no_gas_sl.sum()+no_liq_sl.sum());
127 double const an_no_sum( an_no_gas_sl.sum()+an_no_liq_sl.sum());
128 double const nh3_gas_sum( sc_.nh3_gas_sl.sum());
129 double const nh3_liq_sum( sc_.nh3_liq_sl.sum()+sb_.nh3_sbl.sum());
130
131 double const n_sbl( sb_.don_sbl.sum() + sb_.nh4_sbl.sum()
132 + sb_.urea_sbl.sum() + sb_.no3_sbl.sum() + sb_.nh3_sbl.sum());
133 double const n_sol( nh4_sum + nh4_clay_sum + don_sum
134 + nh3_gas_sum + nh3_liq_sum + urea_sum
135 + no3_sum + an_no3_sum + no2_sum + an_no2_sum
136 + n2o_sum + an_n2o_sum + no_sum + an_no_sum);
137
138 double const c_algae_tot( c_algae + c_dead_algae);
139 double const doc_sum( sc_.doc_sl.sum());
140 double const an_doc_sum( sc_.an_doc_sl.sum());
141 double const acetate_sum( ae_acetate_sl.sum() + an_acetate_sl.sum());
142 double const ch4_gas_sum( ch4_gas_sl.sum());
143 double const ch4_liq_sum( ch4_liq_sl.sum());
144
145 double const c_sol( doc_sum + an_doc_sum + acetate_sum + ch4_gas_sum + ch4_liq_sum);
146
147 double soc20( 0.0);
148 double soc40( 0.0);
149 double totn20( 0.0);
150 double totn40( 0.0);
151 double soilmass20( 0.0);
152 double soilmass40( 0.0);
153 double anvf_avg( 0.0);
154#ifdef METRX_ANVF_TYPES
155 double anvf_avg_pnet( 0.0);
156 double anvf_avg_dndc_can( 0.0);
157 double anvf_avg_nloss( 0.0);
158#endif
159 double pore_connect_avg( 0.0);
160 double d_eff_avg( 0.0);
161 double wfps_avg( 0.0);
162 double air_avg( 0.0);
163 double root_conduct_avg( 0.0);
164 double o2_sum( 0.0);
165 double depth_sum( 0.0);
166
167 double nitrification_inhibition( 0.0);
168 double urease_inhibition( 0.0);
169
170 double mineral_efficiency_scale_sum( 0.0);
171 double mineral_efficiency( 0.0);
172 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
173 {
174 double const c_mic_sl( sc_.C_micro1_sl[sl] + sc_.C_micro2_sl[sl] + sc_.C_micro3_sl[sl]);
175 double const n_mic_sl( n_micro_1_sl[sl] + n_micro_2_sl[sl] + n_micro_3_sl[sl]);
176 mineral_efficiency += MeTrX_get_mineral_efficiency( c_mic_sl / n_mic_sl, cn_opt_mic_sl[sl]) * c_mic_sl;
177 mineral_efficiency_scale_sum += c_mic_sl;
178
179 anvf_avg += sc_.anvf_sl[sl] * sc_.h_sl[sl];
180#ifdef METRX_ANVF_TYPES
181 anvf_avg_pnet += anvf_pnet_sl[sl] * sc_.h_sl[sl];
182 anvf_avg_dndc_can += anvf_dndccan_sl[sl] * sc_.h_sl[sl];
183 anvf_avg_nloss += anvf_nloss_sl[sl] * sc_.h_sl[sl];
184#endif
185 pore_connect_avg += pore_connectivity_sl[sl] * sc_.h_sl[sl];
186 d_eff_avg += D_eff_air_sl[sl] * sc_.h_sl[sl];
187 wfps_avg += MeTrX_get_wfps( sl) * sc_.h_sl[sl];
188 air_avg += (v_air_sl[sl] / sc_.h_sl[sl]) * sc_.h_sl[sl];
189 root_conduct_avg += D_eff_plant_sl[sl] * sc_.h_sl[sl];
190 o2_sum += o2_gas_sl[sl] + o2_liq_sl[sl];
191 depth_sum += sc_.h_sl[sl];
192
193 if ( cbm::flt_less_equal( sc_.depth_sl[sl], 0.2))
194 {
195 soc20 += sc_.C_aorg_sl[sl] +c_humus_1_sl[sl]+c_humus_2_sl[sl]+c_humus_3_sl[sl]
196 + sc_.C_micro1_sl[sl]+sc_.C_micro2_sl[sl]+sc_.C_micro3_sl[sl]
197 + sc_.C_lit1_sl[sl]+sc_.C_lit2_sl[sl]+sc_.C_lit3_sl[sl];
198 totn20 += sc_.N_aorg_sl[sl] +n_humus_1_sl[sl]+n_humus_2_sl[sl]+n_humus_3_sl[sl]
199 + sc_.N_micro_sl[sl] +sc_.N_lit1_sl[sl]+sc_.N_lit2_sl[sl]+sc_.N_lit3_sl[sl];
200 soilmass20 += sc_.dens_sl[sl] * cbm::DM3_IN_M3 * sc_.h_sl[sl];
201 }
202
203 if ( cbm::flt_less_equal( sc_.depth_sl[sl], 0.4))
204 {
205 soc40 += sc_.C_aorg_sl[sl] +c_humus_1_sl[sl]+c_humus_2_sl[sl]+c_humus_3_sl[sl]
206 + sc_.C_micro1_sl[sl]+sc_.C_micro2_sl[sl]+sc_.C_micro3_sl[sl]
207 + sc_.C_lit1_sl[sl]+sc_.C_lit2_sl[sl]+sc_.C_lit3_sl[sl];
208 totn40 += sc_.N_aorg_sl[sl] +n_humus_1_sl[sl]+n_humus_2_sl[sl]+n_humus_3_sl[sl]
209 + sc_.N_micro_sl[sl] +sc_.N_lit1_sl[sl]+sc_.N_lit2_sl[sl]+sc_.N_lit3_sl[sl];
210 soilmass40 += sc_.dens_sl[sl] * cbm::DM3_IN_M3 * sc_.h_sl[sl];
211 }
212 }
213
214 int ui_counter( 0);
215 int ni_counter( 0);
216 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
217 {
218 double const ui_inhibition( crnf_.get_urease_inhibition( sc_.ui_sl[sl]));
219 if ( cbm::flt_greater_zero( ui_inhibition))
220 {
221 ui_counter += 1;
222 urease_inhibition += ui_inhibition;
223 }
224 double const ni_inhibition( crnf_.get_nitrification_inhibition( sc_.ni_sl[sl]));
225 if ( cbm::flt_greater_zero( ni_inhibition))
226 {
227 ni_counter += 1;
228 nitrification_inhibition += ni_inhibition;
229 }
230 }
231
232 if ( ui_counter > 0)
233 {
234 urease_inhibition /= ui_counter;
235 }
236 if ( ni_counter > 0)
237 {
238 nitrification_inhibition /= ni_counter;
239 }
240
241 double const litter_height( (sl_.soil_layers_in_litter_cnt() > 0) ? sc_.depth_sl[sl_.soil_layers_in_litter_cnt()-1] : 0.0);
242 anvf_avg /= depth_sum;
243#ifdef METRX_ANVF_TYPES
244 anvf_avg_pnet /= depth_sum;
245 anvf_avg_dndc_can /= depth_sum;
246 anvf_avg_nloss /= depth_sum;
247#endif
248 pore_connect_avg /= depth_sum;
249 d_eff_avg /= depth_sum;
250 wfps_avg /= depth_sum;
251 air_avg /= depth_sum;
252 root_conduct_avg /= depth_sum;
253
254 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( anvf_avg);
255#ifdef METRX_ANVF_TYPES
256 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( anvf_avg_pnet);
257 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( anvf_avg_dndc_can);
258 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( anvf_avg_nloss);
259#endif
260 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( pore_connect_avg);
261 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( d_eff_avg);
262 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( wfps_avg);
263 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( air_avg);
264 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( root_conduct_avg);
265 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( o2_sum * cbm::M2_IN_HA);
266 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( crnf_.get_crnf_teff_mean());
267 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( crnf_.get_crnf_release_fraction_mean());
268 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( nitrification_inhibition);
269 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( urease_inhibition);
270 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( mineral_efficiency / mineral_efficiency_scale_sum);
271 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( don_sum * cbm::M2_IN_HA);
272 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( nh4_sum * cbm::M2_IN_HA);
273 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( nh4_clay_sum * cbm::M2_IN_HA);
274 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( coated_nh4_sum * cbm::M2_IN_HA);
275 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( urea_sum * cbm::M2_IN_HA);
276 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( no2_sum * cbm::M2_IN_HA);
277 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( an_no2_sum * cbm::M2_IN_HA);
278 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( no3_sum * cbm::M2_IN_HA);
279 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( an_no3_sum * cbm::M2_IN_HA);
280 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n2o_sum * cbm::M2_IN_HA);
281 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( an_n2o_sum * cbm::M2_IN_HA);
282 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( no_sum * cbm::M2_IN_HA);
283 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( an_no_sum * cbm::M2_IN_HA);
284 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( nh3_gas_sum * cbm::M2_IN_HA);
285 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( nh3_liq_sum * cbm::M2_IN_HA);
286 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( doc_sum * cbm::M2_IN_HA);
287 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( an_doc_sum * cbm::M2_IN_HA);
288 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( acetate_sum * cbm::M2_IN_HA);
289 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( ch4_gas_sum * cbm::M2_IN_HA);
290 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( ch4_liq_sum * cbm::M2_IN_HA);
291 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_aorg * cbm::M2_IN_HA);
292 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_aorg * cbm::M2_IN_HA);
293 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_mic_1 * cbm::M2_IN_HA);
294 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_mic_2 * cbm::M2_IN_HA);
295 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_mic_3 * cbm::M2_IN_HA);
296 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_mic_1 * cbm::M2_IN_HA);
297 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_mic_2 * cbm::M2_IN_HA);
298 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_mic_3 * cbm::M2_IN_HA);
299 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_hum_1 * cbm::M2_IN_HA);
300 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_hum_2 * cbm::M2_IN_HA);
301 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_hum_3 * cbm::M2_IN_HA);
302 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_hum_1 * cbm::M2_IN_HA);
303 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_hum_2 * cbm::M2_IN_HA);
304 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_hum_3 * cbm::M2_IN_HA);
305 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_litter_soil_1 * cbm::M2_IN_HA);
306 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_litter_soil_2 * cbm::M2_IN_HA);
307 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_litter_soil_3 * cbm::M2_IN_HA);
308 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_litter_soil_1 * cbm::M2_IN_HA);
309 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_litter_soil_2 * cbm::M2_IN_HA);
310 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_litter_soil_3 * cbm::M2_IN_HA);
311 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_algae_tot * cbm::M2_IN_HA);
312 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_algae_tot * cbm::M2_IN_HA);
313 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_stub * cbm::M2_IN_HA);
314 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_stub * cbm::M2_IN_HA);
315 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_litter_above * cbm::M2_IN_HA);
316 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_litter_above * cbm::M2_IN_HA);
317 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (c_wood + c_aorg + c_mic_1 + c_mic_2 + c_mic_3 +
318 c_hum_1 + c_hum_2 + c_hum_3 + c_litter_soil_1 + c_litter_soil_2 + c_litter_soil_3 +
319 c_algae + c_stub + c_sol) * cbm::M2_IN_HA);
320 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (n_wood + n_aorg + n_mic_1 + n_mic_2 + n_mic_3 +
321 n_hum_1 + n_hum_2 + n_hum_3 + n_litter_soil_1 + n_litter_soil_2 + n_litter_soil_3 +
322 n_algae + n_stub + n_sol) * cbm::M2_IN_HA);
323
324 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_sbl * cbm::M2_IN_HA);
325
326 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( soc20 / soilmass20);
327 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( soc40 / soilmass40);
328 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( totn20 / soilmass20);
329 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( totn40 / soilmass40);
330 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.fe2_sl.sum() * cbm::M2_IN_HA);
331 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.fe3_sl.sum() * cbm::M2_IN_HA);
332 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.till_effect_sl.sum() / sl_.soil_layer_cnt());
333 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( freeze_thaw_fact_sl.sum());
334 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( litter_height);
335 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( MeTrX_get_ph_wl());
336 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.ph_sl[0]);
337 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_no3_groundwater_access * cbm::M2_IN_HA);
338 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (day_assi_n_mic_1+day_assi_n_mic_2+day_assi_n_mic_3) * cbm::M2_IN_HA);
339 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_nit_nh4_no2 * cbm::M2_IN_HA);
340 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_nit_no2_no3_sl.sum() * cbm::M2_IN_HA);
341 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_nit_no2_no * cbm::M2_IN_HA);
342 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_nit_no2_n2o * cbm::M2_IN_HA);
343 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_denit_no3_no2 * cbm::M2_IN_HA);
344 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_denit_no2_no * cbm::M2_IN_HA);
345 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_denit_no2_n2o * cbm::M2_IN_HA);
346 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_denit_no2_n2 * cbm::M2_IN_HA);
347 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_denit_no_n2o * cbm::M2_IN_HA);
348 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_denit_no_n2 * cbm::M2_IN_HA);
349 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_denit_n2o_n2 * cbm::M2_IN_HA);
350 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_chemodenit_no2_no * cbm::M2_IN_HA);
351 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_ch4_oxidation_sl.sum() * cbm::M2_IN_HA);
352 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_ch4_production_hydrogen_sl.sum() * cbm::M2_IN_HA);
353 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_ch4_production_acetate_sl.sum() * cbm::M2_IN_HA);
354 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_ch4_plant.sum() * cbm::M2_IN_HA);
355 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_ch4_soil.sum() * cbm::M2_IN_HA);
356 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_ch4_water.sum() * cbm::M2_IN_HA);
357 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_ch4_bubbling.sum() * cbm::M2_IN_HA);
358 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_ch4_leach.sum() * cbm::M2_IN_HA);
359 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_o2_plant.sum() * cbm::M2_IN_HA);
360
361 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (sc_.accumulated_c_litter_stubble + sc_.accumulated_c_litter_wood_above - accumulated_c_litter_above_old) * cbm::M2_IN_HA);
362 accumulated_c_litter_above_old = sc_.accumulated_c_litter_stubble + sc_.accumulated_c_litter_wood_above;
363
364 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (sc_.accumulated_c_litter_below_sl.sum() + sc_.accumulated_c_litter_wood_below_sl.sum() - accumulated_c_litter_below_old) * cbm::M2_IN_HA);
365 accumulated_c_litter_below_old = sc_.accumulated_c_litter_below_sl.sum() + sc_.accumulated_c_litter_wood_below_sl.sum();
366
367 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_c_fix_algae * cbm::M2_IN_HA);
368 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_n_fix_algae * cbm::M2_IN_HA);
369 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (day_decomp_c_lit_1+day_decomp_c_lit_2+day_decomp_c_lit_3) * cbm::M2_IN_HA);
370 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_decay_c_mic_sl.sum()*cbm::M2_IN_HA);
371 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_co2_prod_mic_1_growth * cbm::M2_IN_HA);
372 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_co2_prod_mic_1_maintenance * cbm::M2_IN_HA);
373 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_co2_prod_mic_2 * cbm::M2_IN_HA);
374 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_co2_prod_mic_3_acetate_prod * cbm::M2_IN_HA);
375 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_co2_prod_mic_3_acetate_cons * cbm::M2_IN_HA);
376 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_co2_prod_ch4_prod * cbm::M2_IN_HA);
377 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_co2_prod_ch4_cons * cbm::M2_IN_HA);
378 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_h2_c_eq_prod_sl.sum() * cbm::M2_IN_HA);
379 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_acetate_prod_sl.sum() * cbm::M2_IN_HA);
380 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_acetate_cons_fe3_sl.sum() * cbm::M2_IN_HA/FE3_ACETATE_REDUCTION_RATIO);
381 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_h2_c_eq_cons_fe3_sl.sum() * cbm::M2_IN_HA/FE3_ACETATE_REDUCTION_RATIO);
382 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_doc_prod_decomp_litter * cbm::M2_IN_HA);
383 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_doc_prod_decomp_humus * cbm::M2_IN_HA);
384 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_doc_prod_decomp_aorg * cbm::M2_IN_HA);
385 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( dC_root_exsudates * cbm::M2_IN_HA);
386 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_c_humify_doc_hum_2_sl.sum() * cbm::M2_IN_HA);
387 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_c_humify_sol_hum_1_sl.sum() * cbm::M2_IN_HA);
388 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_c_humify_cel_hum_1_sl.sum() * cbm::M2_IN_HA);
389 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_c_humify_lig_hum_1_sl.sum() * cbm::M2_IN_HA);
390 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_c_humify_lig_hum_2_sl.sum() * cbm::M2_IN_HA);
391 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_c_humify_mic_hum_1_sl.sum() * cbm::M2_IN_HA);
392 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_c_humify_mic_hum_2_sl.sum() * cbm::M2_IN_HA);
393 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_c_humify_hum_1_hum_2_sl.sum() * cbm::M2_IN_HA);
394 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_c_humify_hum_2_hum_3_sl.sum() * cbm::M2_IN_HA);
395 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_min_n_decomp * cbm::M2_IN_HA);
396 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_min_n_aorg * cbm::M2_IN_HA);
397 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_min_n_mic_1 * cbm::M2_IN_HA);
398 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_min_n_mic_2 * cbm::M2_IN_HA);
399 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_min_n_mic_3 * cbm::M2_IN_HA);
400 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_assi_c_mic_1 * cbm::M2_IN_HA);
401 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_assi_c_mic_2 * cbm::M2_IN_HA);
402 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_assi_c_mic_3 * cbm::M2_IN_HA);
403
404 return output_writer_.write_daily( output_data_);
405}

References MeTrX_get_ph_wl().

Referenced by MeTrX_write_output().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ MeTrX_write_output_fluxes()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_write_output_fluxes ( )
private
Parameters
[in]None
[out]None
Returns
error code
726{
727#define METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH(__val__) \
728{ \
729double const delta_val( __val__ - output_writer_.output_writer_fluxes.__val__); \
730LDNDC_OUTPUT_SET_COLUMN_((delta_val),=,output_data_,1); \
731output_writer_.output_writer_fluxes.__val__ = __val__; \
732} \
733
734#define METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH_2(__val1__,__val2__) \
735{ \
736double const delta_val( __val1__ - output_writer_.output_writer_fluxes.__val2__); \
737LDNDC_OUTPUT_SET_COLUMN_((delta_val),=,output_data_,1); \
738output_writer_.output_writer_fluxes.__val2__ = __val1__; \
739} \
740
741 for ( size_t l = 0; l < sl_.soil_layer_cnt(); ++l)
742 {
743 LDNDC_OUTPUT_SET_COLUMN_INDEX(0);
744 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( -sc_.depth_sl[l]);
745
746 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_throughfall_sl[l]);
747 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_throughfall_sl[l]);
748 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_throughfall_sbl[l]);
749 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_throughfall_sbl[l]);
750
751 //N fluxes in plant/algae
752 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_to_living_plant_and_algae_from_extern_sl[l]);
753 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH_2( ph_.accumulated_nh4_uptake_sl[l], accumulated_n_plant_nh4_uptake_sl[l]);
754 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH_2( ph_.accumulated_no3_uptake_sl[l], accumulated_n_plant_no3_uptake_sl[l]);
755 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH_2( ph_.accumulated_nh3_uptake_sl[l], accumulated_n_plant_nh3_uptake_sl[l]);
756 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH_2( ph_.accumulated_don_uptake_sl[l], accumulated_n_plant_don_uptake_sl[l]);
757 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_algae_nh4_uptake_sbl[l]);
758 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_algae_no3_uptake_sbl[l]);
759 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_algae_nh3_uptake_sbl[l]);
760
761 //N fluxes from plant to raw litter, stubble and wood
762 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_from_plants_below_rawlitter_sl[l]);
763 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_from_plants_below_wood_sl[l]);
764 if ( l == 0)
765 {
766 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_from_plants_above_rawlitter);
767 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_from_plants_above_wood);
768 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_from_plants_above_stubble);
769 }
770 else
771 {
772 LDNDC_OUTPUT_SET_COLUMN_(0.0,=,output_data_,1);
773 LDNDC_OUTPUT_SET_COLUMN_(0.0,=,output_data_,1);
774 LDNDC_OUTPUT_SET_COLUMN_(0.0,=,output_data_,1);
775 }
776
777 //N fluxes from raw litter to soil litter
778 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_aboveground_raw_litter_fragmentation_sl[l]);
779 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_belowground_raw_litter_fragmentation_sl[l]);
780
781 //N fluxes from grazer and algae
782 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_from_algae_sl[l]);
783 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_from_dung_sl[l]);
784 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_urea_from_dung_sl[l]);
785
786 //N exported via harvesting, cutting and grazing
787 if ( l == 0)
788 {
789 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_export_harvest_cutting_grazing);
790 }
791 else
792 {
793 LDNDC_OUTPUT_SET_COLUMN_(0.0,=,output_data_,1);
794 }
795
796 //N fluxes from fertilization and manuring
797 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_fertilization_sl[l]);
798 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_fertilization_sl[l]);
799 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_fertilization_sl[l]);
800 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_don_fertilization_sl[l]);
801 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_urea_fertilization_sl[l]);
802 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_fertilization_sl[l]);
803 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_aorg_fertilization_sl[l]);
804 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_fertilization_sbl[l]);
805 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_fertilization_sbl[l]);
806 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_fertilization_sbl[l]);
807 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_urea_fertilization_sbl[l]);
808
809 //N redistribution during tilling
810 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_surface_litter_incorporation_via_tilling_sl[l]);
811 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_tilling_sl[l]);
812 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_aorg_tilling_sl[l]);
813 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_1_tilling_sl[l]);
814 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_2_tilling_sl[l]);
815 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_3_tilling_sl[l]);
816 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_tilling_sl[l]);
817 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no2_tilling_sl[l]);
818 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no_tilling_sl[l]);
819 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_n2o_tilling_sl[l]);
820 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_urea_tilling_sl[l]);
821 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_don_tilling_sl[l]);
822 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_tilling_sl[l]);
823 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_tilling_sl[l]);
824 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_microbes_tilling_sl[l]);
825
826 //N redistribution during spin up
827 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_1_spinup_sl[l]);
828 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_2_spinup_sl[l]);
829 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_3_spinup_sl[l]);
830 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_surface_litter_spinup_sl[l]);
831 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_spinup_sl[l]);
832
833 //N fluxes due to water movement
834 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_micro_leaching_sl[l]);
835 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_aorg_leaching_sl[l]);
836 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_leaching_sl[l]);
837 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_1_leaching_sl[l]);
838 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_2_leaching_sl[l]);
839 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_3_leaching_sl[l]);
840 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_leaching_sl[l]);
841 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH_2( sc_.accumulated_n_no3_leaching_sl[l], accumulated_n_no3_leaching_sl[l]);
842 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_leaching_sl[l]);
843 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_don_leaching_sl[l]);
844 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_urea_leaching_sl[l]);
845 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no_leaching_sl[l]);
846 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_n2o_leaching_sl[l]);
847
848 //N fluxes via liquid diffusion
849 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_urea_liq_diffusion_sl[l]);
850 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_liq_diffusion_sl[l]);
851 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_liq_diffusion_sl[l]);
852 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_liq_diffusion_sl[l]);
853
854 // incoming N from leaching from surface water
855 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_infiltration_phys_sl[l]);
856 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_infiltration_phys_sl[l]);
857 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_urea_infiltration_phys_sl[l]);
858 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_infiltration_phys_sl[l]);
859 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_don_infiltration_phys_sl[l]);
860 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_aorg_infiltration_phys_sl[l]);
861
862 //incoming N fluxes from disappearing water table
863 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_infiltration_leach_sl[l]);
864 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_infiltration_leach_sl[l]);
865 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_urea_infiltration_leach_sl[l]);
866 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_infiltration_leach_sl[l]);
867 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_don_infiltration_leach_sl[l]);
868 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no_infiltration_leach_sl[l]);
869 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_n2o_infiltration_leach_sl[l]);
870
871 //incoming N flux via liquid diffusion from surface water
872 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_infiltration_liqdif_sl[l]);
873 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_infiltration_liqdif_sl[l]);
874 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_urea_infiltration_liqdif_sl[l]);
875 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_infiltration_liqdif_sl[l]);
876
877 //ebullition fluxes
878 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_bubbling_sl[l]);
879 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no_bubbling_sl[l]);
880 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_n2o_bubbling_sl[l]);
881 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_bubbling_sbl[l]);
882 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no_bubbling_sbl[l]);
883 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_n2o_bubbling_sbl[l]);
884
885 //N fluxes due to dissolution between atmosphere and surface water
886 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_dissolution_sbl[l]);
887 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no_dissolution_sbl[l]);
888 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_n2o_dissolution_sbl[l]);
889
890 //N fluxes from urea to nh4
891 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_urea_nh4_hydrolysis_sl[l]);
892 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_urea_nh4_hydrolysis_sbl[l]);
893
894 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_assimilation_sl[l]);
895 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_assimilation_sl[l]);
896 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_don_assimilation_sl[l]);
897
898 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_nh3_conversion_sl[l]);
899 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_nh4_conversion_sl[l]);
900 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_nh3_conversion_sbl[l]);
901 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_nh4_conversion_sbl[l]);
902
903 //gaseous diffusion
904 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_phys_diffusion_sl[l]);
905 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no_phys_diffusion_sl[l]);
906 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_n2o_phys_diffusion_sl[l]);
907 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh3_gas_diffusion_sl[l]);
908 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no_gas_diffusion_sl[l]);
909 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_n2o_gas_diffusion_sl[l]);
910
911 //perturbation
912 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_micro_perturbation_sl[l]);
913 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_aorg_perturbation_sl[l]);
914 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_perturbation_sl[l]);
915 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_1_perturbation_sl[l]);
916 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_2_perturbation_sl[l]);
917 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_3_perturbation_sl[l]);
918
919 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_no2_nitrification_sl[l]);
920 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_no_nitrification_sl[l]);
921 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_nh4_n2o_nitrification_sl[l]);
922 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no2_no3_nitrification_sl[l]);
923
924 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_no2_denitrification_sl[l]);
925 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_no_denitrification_sl[l]);
926 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_n2o_denitrification_sl[l]);
927 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no3_n2_denitrification_sl[l]);
928 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no2_no_denitrification_sl[l]);
929 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no2_n2o_denitrification_sl[l]);
930 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no2_n2_denitrification_sl[l]);
931 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no_n2o_denitrification_sl[l]);
932 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no_n2_denitrification_sl[l]);
933 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_n2o_n2_denitrification_sl[l]);
934
935 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_no2_chemodenitrification_sl[l]);
936
937 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_mic_naorg_decay_sl[l]);
938 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_mic_nh4_mineral_sl[l]);
939 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_mic_don_dissolve_sl[l]);
940
941 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_aorg_nh4_mineral_sl[l]);
942 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_aorg_don_dissolve_sl[l]);
943
944 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_1_don_dissolve_sl[l]);
945 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_1_nh4_mineral_sl[l]);
946 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_2_don_dissolve_sl[l]);
947 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_2_nh4_mineral_sl[l]);
948 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_3_don_dissolve_sl[l]);
949 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_humus_3_nh4_mineral_sl[l]);
950
951 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_don_dissolve_sl[l]);
952 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_nh4_mineral_sl[l]);
953
954 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_don_humus_1_humify_sl[l]);
955 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_don_humus_2_humify_sl[l]);
956 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_don_humus_3_humify_sl[l]);
957 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT_AND_SWITCH( accumulated_n_litter_humus_1_humify_sl[l]);
958
959 lerr_t rc_write = output_writer_.write_fluxes( l, output_data_);
960 if ( rc_write)
961 {
962 return LDNDC_ERR_FAIL;
963 }
964 }
965
966 return LDNDC_ERR_OK;
967}

Referenced by MeTrX_write_output().

Here is the caller graph for this function:

◆ MeTrX_write_output_layer_daily()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_write_output_layer_daily ( )
private
Parameters
[in]None
[out]None
Returns
error code
454{
455 size_t fl_cnt( m_veg->canopy_layers_used());
456 size_t sbl_cnt( sb_.surfacebulk_layer_cnt());
457
458 for ( size_t fl = fl_cnt; fl > 0; --fl)
459 {
460 size_t l( fl-1);
461 LDNDC_OUTPUT_SET_COLUMN_INDEX(0);
462 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //depth
463 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( ph_.h_fl[l]); //extension
464 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //pH
465 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //pore_connectivity
466 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( D_eff_air_fl[l]); //air permeability
467 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //aerenchym_permeability
468 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //cfdd
469 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //water_content
470 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //air_content
471 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //porosity
472 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //fe2
473 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //fe3
474 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( ts_co2_concentration_fl[l]*cbm::M2_IN_HA);
475 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( ts_ch4_concentration_fl[l]*cbm::M2_IN_HA);
476 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //ch4 bubbling
477 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //ch4 production
478 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //ch4 oxidation
479 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //doc production
480 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //acetate production
481 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //mic decay
482 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //doc
483 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //doc
484 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //acetate
485 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //no3
486 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //no3
487 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //nh4
488 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //urea
489 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( nh3_fl[l]*cbm::M2_IN_HA);
490 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //o2
491 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //o2 consumption
492 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( ts_no_concentration_fl[l]*cbm::M2_IN_HA);
493 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //n2o
494 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //c_humus_0
495 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //c_humus_1
496 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //c_humus_2
497 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //no3_cons_denit
498 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //denit_factor_c
499 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //denit_factor_n
500 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //no3_prod_nit
501 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //no3_leaching
502
503 lerr_t rc_write = output_writer_.write_layer_daily( -static_cast< int >( fl+sbl_cnt+1), output_data_);
504 if ( rc_write)
505 {
506 return LDNDC_ERR_FAIL;
507 }
508 }
509
510 for (size_t sbl = sbl_cnt; sbl > 0; --sbl)
511 {
512 double depth_sbl( sbl_cnt * 0.01 - 0.5 * 0.01 - (sbl-1) * 0.01);
513 size_t l( sbl-1);
514 LDNDC_OUTPUT_SET_COLUMN_INDEX(0);
515 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( depth_sbl); //depth
516 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //extension
517 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( MeTrX_get_ph_wl()); //pH
518 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //pore_connectivity
519 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //air permeability
520 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //aerenchym_permeability
521 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //cfdd
522 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //water_content
523 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //air_content
524 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //porosity
525 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //fe2
526 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //fe3
527 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.co2_sbl[l]*cbm::M2_IN_HA);
528 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.ch4_sbl[l]*cbm::M2_IN_HA);
529
530 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (accumulated_c_ch4_bubbling_sbl[l]-
531 output_writer_.output_writer_layer_daily.accumulated_c_ch4_bubbling_sbl[l])*cbm::M2_IN_HA);
532 output_writer_.output_writer_layer_daily.accumulated_c_ch4_bubbling_sbl[l] = accumulated_c_ch4_bubbling_sbl[l];
533
534 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //ch4 production
535 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //ch4 oxidation
536 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //doc production
537 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //acetate production
538 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //mic decay
539 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //doc
540 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.doc_sbl[l]*cbm::M2_IN_HA);
541 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //acetate
542 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //no3 ae
543 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.no3_sbl[l]*cbm::M2_IN_HA);
544 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.nh4_sbl[l]*cbm::M2_IN_HA);
545 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.urea_sbl[l]*cbm::M2_IN_HA);
546 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.nh3_sbl[l]*cbm::M2_IN_HA);
547 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.o2_sbl[l]*cbm::M2_IN_HA);
548 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //o2 consumption
549 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //no
550 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //n2o
551 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //c_humus_0
552 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //c_humus_1
553 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //c_humus_2
554 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //no3_cons_denit
555 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //denit_factor_c
556 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //denit_factor_n
557 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //no3_prod_nit
558 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0.0); //no3_leaching
559
560 lerr_t rc_write = output_writer_.write_layer_daily( -static_cast< int >( sbl), output_data_);
561 if ( rc_write)
562 {
563 return LDNDC_ERR_FAIL;
564 }
565 }
566
567 for ( size_t l = 0; l < sl_.soil_layer_cnt(); ++l)
568 {
569 LDNDC_OUTPUT_SET_COLUMN_INDEX(0);
570 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( -sc_.depth_sl[l]);
571 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.h_sl[l]);
572 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.ph_sl[l]);
573 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( pore_connectivity_sl[l]);
574 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( D_eff_air_sl[l]);
575 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( D_eff_plant_sl[l]);
576 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( cumulative_freezing_degree_days_sl[l]);
577 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( wc_.wc_sl[l]);
578 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( v_air_sl[l]/sc_.h_sl[l]);
579 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.poro_sl[l]);
580 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.fe2_sl[l]*cbm::M2_IN_HA);
581 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.fe3_sl[l]*cbm::M2_IN_HA);
582 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (co2_liq_sl[l]+co2_gas_sl[l])*cbm::M2_IN_HA);
583 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (ch4_liq_sl[l]+ch4_gas_sl[l])*cbm::M2_IN_HA);
584 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (accumulated_c_ch4_bubbling_sl[l]-
585 output_writer_.output_writer_layer_daily.accumulated_c_ch4_bubbling_sl[l])*cbm::M2_IN_HA);
586 output_writer_.output_writer_layer_daily.accumulated_c_ch4_bubbling_sl[l] = accumulated_c_ch4_bubbling_sl[l];
587 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (day_ch4_production_acetate_sl[l]+day_ch4_production_hydrogen_sl[l])*cbm::M2_IN_HA);
588 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_ch4_oxidation_sl[l]*cbm::M2_IN_HA);
589 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_doc_prod_sl[l]*cbm::M2_IN_HA);
590 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_acetate_prod_sl[l]*cbm::M2_IN_HA);
591 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_decay_c_mic_sl[l]*cbm::M2_IN_HA);
592 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (sc_.doc_sl[l])*cbm::M2_IN_HA);
593 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (sc_.an_doc_sl[l])*cbm::M2_IN_HA);
594 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (ae_acetate_sl[l]+an_acetate_sl[l])*cbm::M2_IN_HA);
595 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (no3_ae_sl[l])*cbm::M2_IN_HA);
596 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (no3_an_sl[l])*cbm::M2_IN_HA);
597 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (nh4_ae_sl[l]+nh4_an_sl[l]+sc_.clay_nh4_sl[l])*cbm::M2_IN_HA);
598 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.urea_sl[l]*cbm::M2_IN_HA);
599 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (sc_.nh3_gas_sl[l]+sc_.nh3_liq_sl[l])*cbm::M2_IN_HA);
600 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (o2_gas_sl[l]+o2_liq_sl[l])*cbm::M2_IN_HA);
601 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( o2_consumption_sl[l]*cbm::M2_IN_HA);
602 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (no_liq_sl[l]+no_gas_sl[l]+an_no_liq_sl[l]+an_no_gas_sl[l])*cbm::M2_IN_HA);
603 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (n2o_liq_sl[l]+n2o_gas_sl[l]+an_n2o_liq_sl[l]+an_n2o_gas_sl[l])*cbm::M2_IN_HA);
604 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_humus_1_sl[l]*cbm::M2_IN_HA);
605 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_humus_2_sl[l]*cbm::M2_IN_HA);
606 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_humus_3_sl[l]*cbm::M2_IN_HA);
607 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (accumulated_n_no3_no2_denitrification_sl[l]
608 -output_writer_.output_writer_layer_daily.accumulated_n_no3_no2_denitrification_sl[l]) * cbm::M2_IN_HA);
609 output_writer_.output_writer_layer_daily.accumulated_n_no3_no2_denitrification_sl[l] = accumulated_n_no3_no2_denitrification_sl[l];
610 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_denit_factor_c_sl[l]*FTS_TOT_);
611 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_denit_factor_n_sl[l]*FTS_TOT_);
612 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( day_nit_no2_no3_sl[l]*cbm::M2_IN_HA);
613 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( (sc_.accumulated_n_no3_leaching_sl[l]
614 -output_writer_.output_writer_layer_daily.accumulated_n_no3_leaching_sl[l]) * cbm::M2_IN_HA);
615 output_writer_.output_writer_layer_daily.accumulated_n_no3_leaching_sl[l] = sc_.accumulated_n_no3_leaching_sl[l];
616
617 lerr_t rc_write = output_writer_.write_layer_daily( l, output_data_);
618 if ( rc_write)
619 {
620 return LDNDC_ERR_FAIL;
621 }
622 }
623
624 return LDNDC_ERR_OK;
625}

References MeTrX_get_ph_wl().

Referenced by MeTrX_write_output().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ MeTrX_write_output_layer_yearly()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_write_output_layer_yearly ( )
private
Parameters
[in]None
[out]None
Returns
error code
630{
631 for ( size_t l = 0; l < sl_.soil_layer_cnt(); ++l)
632 {
633 LDNDC_OUTPUT_SET_COLUMN_INDEX(0);
634 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( -sc_.depth_sl[l]);
635 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_humus_1_sl[l]);
636 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_humus_2_sl[l]);
637 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_humus_3_sl[l]);
638 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.C_aorg_sl[l]);
639 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.C_micro1_sl[l]+sc_.C_micro2_sl[l]+sc_.C_micro3_sl[l]);
640
641 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( accumulated_n_no3_no2_denitrification_sl[l] - output_writer_.output_writer_layer_yearly.accumulated_n_no3_no2_denitrification_sl[l]);
642 output_writer_.output_writer_layer_yearly.accumulated_n_no3_no2_denitrification_sl[l] = accumulated_n_no3_no2_denitrification_sl[l];
643
644 lerr_t rc_write = output_writer_.write_layer_yearly( l, output_data_);
645 if ( rc_write)
646 {
647 return LDNDC_ERR_FAIL;
648 }
649 }
650
651 return LDNDC_ERR_OK;
652}

Referenced by MeTrX_write_output().

Here is the caller graph for this function:

◆ MeTrX_write_output_pools()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_write_output_pools ( )
private
Parameters
[in]None
[out]None
Returns
error code
657{
658 for ( size_t l = 0; l < sl_.soil_layer_cnt(); ++l)
659 {
660 LDNDC_OUTPUT_SET_COLUMN_INDEX(0);
661 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( -sc_.depth_sl[l]);
662
663 //pools that exist for each soil layer
664 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.urea_sl[l]);
665 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.N_lit1_sl[l] + sc_.N_lit2_sl[l] + sc_.N_lit3_sl[l] + sc_.n_wood_sl[l] + sc_.n_raw_lit_1_sl[l] + sc_.n_raw_lit_2_sl[l] + sc_.n_raw_lit_3_sl[l]);
666 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.N_aorg_sl[l]);
667 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_humus_1_sl[l]);
668 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_humus_2_sl[l]);
669 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_humus_3_sl[l]);
670 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n_micro_1_sl[l] + n_micro_2_sl[l] + n_micro_3_sl[l]);
671 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.nh3_liq_sl[l] + sc_.nh3_gas_sl[l]);
672 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( nh4_ae_sl[l] + nh4_an_sl[l] + sc_.clay_nh4_sl[l]);
673 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( don_ae_sl[l] + don_an_sl[l]);
674 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( no3_ae_sl[l] + no3_an_sl[l]);
675 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.no2_sl[l] + sc_.an_no2_sl[l]);
676 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( no_gas_sl[l] + an_no_gas_sl[l] + no_liq_sl[l] + an_no_liq_sl[l]);
677 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( n2o_gas_sl[l] + an_n2o_gas_sl[l] + n2o_liq_sl[l] + an_n2o_liq_sl[l]);
678
679 //surface pools
680 if( l == 0 )
681 {
682 double nplant(0.0);
683 for ( PlantIterator vt = this->m_veg->begin(); vt != this->m_veg->end(); ++vt)
684 {
685 nplant += (*vt)->total_nitrogen();
686 }
687
688 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.nh4_sbl.sum() );
689 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.nh3_sbl.sum() );
690 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.n2o_sbl.sum() );
691 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.no_sbl.sum() );
692 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.urea_sbl.sum() );
693 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.no3_sbl.sum() );
694 //METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sb_.don_sbl.sum() );
695 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( nplant );
696 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.n_wood + sc_.n_stubble_lit1 + sc_.n_stubble_lit2 + sc_.n_stubble_lit3 +
697 sc_.n_raw_lit_1_above + sc_.n_raw_lit_2_above + sc_.n_raw_lit_3_above);
698 }
699 else
700 {
701 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0 );
702 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0 );
703 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0 );
704 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0 );
705 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0 );
706 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0 );
707 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0 );
708 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0 );
709 //METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0 );
710 //METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( 0 );
711 }
712
713 lerr_t rc_write = output_writer_.write_pools( l, output_data_);
714 if ( rc_write)
715 {
716 return LDNDC_ERR_FAIL;
717 }
718 }
719
720 return LDNDC_ERR_OK;
721}

Referenced by MeTrX_write_output().

Here is the caller graph for this function:

◆ MeTrX_write_output_subdaily()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_write_output_subdaily ( )
private
Parameters
[in]None
[out]None
Returns
error code
972{
973 size_t s( lclock()->subday()-1);
974 LDNDC_OUTPUT_SET_COLUMN_INDEX(0);
975 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.C_micro1_sl.sum());
976 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.C_micro2_sl.sum());
977 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.C_micro3_sl.sum());
978 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.C_aorg_sl.sum());
979 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( nh4_ae_sl.sum()+nh4_an_sl.sum()+sc_.clay_nh4_sl.sum());
980 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( no3_ae_sl.sum());
981 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( no3_an_sl.sum());
982 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.doc_sl.sum());
983 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.an_doc_sl.sum());
984 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( ae_acetate_sl.sum());
985 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( an_acetate_sl.sum());
986
987 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_ch4_bubbling[s]);
988 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_ch4_plant[s]);
989 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_ch4_soil[s]);
990 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_ch4_water[s]);
991 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_ch4_leach[s]);
992 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_ch4_prod[s]);
993 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_ch4_ox[s]);
994
995 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_acetate_prod[s]);
996 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_doc_prod[s]);
997
998 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( accumulated_n_no2_no3_nitrification_sl.sum() - output_writer_.output_writer_subdaily.accumulated_n_no2_no3_nitrification);
999 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( accumulated_n_no3_no2_denitrification_sl.sum() - output_writer_.output_writer_subdaily.accumulated_n_no3_no2_denitrification);
1000
1001 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_n2o_bubbling[s]);
1002 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_n2o_plant[s]);
1003 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_n2o_soil[s]);
1004 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_n2o_water[s]);
1005 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_no_bubbling[s]);
1006 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_no_plant[s]);
1007 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_no_soil[s]);
1008 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_no_water[s]);
1009 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_nh3_bubbling[s]);
1010 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_nh3_plant[s]);
1011 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_nh3_soil[s]);
1012 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_nh3_water[s]);
1013
1014 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_plant_o2_cons[s]);
1015 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_o2_plant[s]);
1016 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( subdaily_algae_o2_prod[s]);
1017
1018 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( MeTrX_get_ph_wl());
1019 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( sc_.ph_sl[0]);
1020 double anvf_mean( sc_.anvf_sl.sum() / sl_.soil_layer_cnt());
1021 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( anvf_mean);
1022
1023 lerr_t rc_write = output_writer_.write_subdaily( output_data_);
1024 if ( rc_write)
1025 {
1026 return LDNDC_ERR_FAIL;
1027 }
1028
1029 output_writer_.output_writer_subdaily.accumulated_n_no2_no3_nitrification = accumulated_n_no2_no3_nitrification_sl.sum();
1030 output_writer_.output_writer_subdaily.accumulated_n_no3_no2_denitrification = accumulated_n_no3_no2_denitrification_sl.sum();
1031
1032 return LDNDC_ERR_OK;
1033}

References MeTrX_get_ph_wl().

Referenced by MeTrX_write_output().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ MeTrX_write_output_yearly()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_write_output_yearly ( )
private
Parameters
[in]None
[out]None
Returns
error code
410{
411 double surface_litter( c_algae + c_dead_algae + sc_.c_stubble_lit1 + sc_.c_stubble_lit2 + sc_.c_stubble_lit3);
412 double soc20( 0.0);
413 double c_hum_1_20( 0.0);
414 double c_hum_2_20( 0.0);
415 double c_hum_3_20( 0.0);
416 double c_litter_20( 0.0);
417 double c_aorg_20( 0.0);
418 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
419 {
420 if ( cbm::flt_less_equal( sc_.depth_sl[sl], 0.2))
421 {
422 soc20 += sc_.C_aorg_sl[sl] + c_humus_1_sl[sl] + c_humus_2_sl[sl] + c_humus_3_sl[sl]
423 + sc_.C_micro1_sl[sl] + sc_.C_micro2_sl[sl] + sc_.C_micro3_sl[sl]
424 + sc_.C_lit1_sl[sl] + sc_.C_lit2_sl[sl] + sc_.C_lit3_sl[sl];
425 c_hum_1_20 += c_humus_1_sl[sl];
426 c_hum_2_20 += c_humus_2_sl[sl];
427 c_hum_3_20 += c_humus_3_sl[sl];
428 c_litter_20 += sc_.C_lit1_sl[sl] + sc_.C_lit2_sl[sl] + sc_.C_lit3_sl[sl];
429 c_aorg_20 += sc_.C_aorg_sl[sl];
430 }
431 else
432 {
433 break;
434 }
435 }
436
437#define METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT(__val__) LDNDC_OUTPUT_SET_COLUMN_((__val__),=,output_data_,1)
438 LDNDC_OUTPUT_SET_COLUMN_INDEX(0);
439
440 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( surface_litter);
441 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( soc20);
442 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_hum_1_20);
443 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_hum_2_20);
444 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_hum_3_20);
445 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_litter_20);
446 METRX_OUTPUT_SET_COLUMN_AND_GOTO_NEXT( c_aorg_20);
447
448 return output_writer_.write_yearly( output_data_);
449}

Referenced by MeTrX_write_output().

Here is the caller graph for this function:

◆ MeTrX_write_rates()

lerr_t ldndc::SoilChemistryMeTrX::MeTrX_write_rates ( )
private
Parameters
[in]None
[out]None
Returns
error code
20{
21 sc_.accumulated_n2_emis = 0.0;
22 for( size_t sl = 0; sl < sl_.soil_layer_cnt(); ++sl)
23 {
24 sc_.no_sl[sl] = no_gas_sl[sl]+no_liq_sl[sl];
25 sc_.an_no_sl[sl] = an_no_gas_sl[sl]+an_no_liq_sl[sl];
26
27 sc_.n2o_sl[sl] = n2o_gas_sl[sl]+n2o_liq_sl[sl];
28 sc_.an_n2o_sl[sl] = an_n2o_gas_sl[sl]+an_n2o_liq_sl[sl];
29
30 sc_.C_hum_sl[sl] = c_humus_1_sl[sl] + c_humus_2_sl[sl] + c_humus_3_sl[sl];
31 sc_.N_hum_sl[sl] = n_humus_1_sl[sl] + n_humus_2_sl[sl] + n_humus_3_sl[sl];
32
33 sc_.N_micro_sl[sl] = n_micro_1_sl[sl] + n_micro_2_sl[sl] + n_micro_3_sl[sl];
34 sc_.som_sl[sl] = (sc_.C_lit1_sl[sl] + sc_.C_lit2_sl[sl] + sc_.C_lit3_sl[sl]
35 + sc_.c_raw_lit_1_sl[sl] + sc_.c_raw_lit_2_sl[sl] + sc_.c_raw_lit_3_sl[sl]
36 + sc_.C_micro1_sl[sl] + sc_.C_micro2_sl[sl] + sc_.C_micro3_sl[sl]
37 + sc_.C_hum_sl[sl] + sc_.C_aorg_sl[sl])
38 / cbm::CCORG;
39
40 sc_.o2_sl[sl] = o2_gas_sl[sl] * RGAS_M_O2_BAR_PA * (mc_temp_sl[sl] + cbm::D_IN_K) / v_air_sl[sl];
41
42 sc_.accumulated_no3_denitrify_sl[sl] = accumulated_n_no3_no2_denitrification_sl[sl];
43 sc_.accumulated_n2_emis += accumulated_n_no3_n2_denitrification_sl[sl]
44 + accumulated_n_no2_n2_denitrification_sl[sl]
45 + accumulated_n_no_n2_denitrification_sl[sl]
46 + accumulated_n_n2o_n2_denitrification_sl[sl];
47 }
48
49 size_t const ts_end( (timemode_ == TMODE_SUBDAILY) ? lclock()->subday() * INTERNAL_TIME_STEPS : INTERNAL_TIME_STEPS);
50 size_t const ts_start( ts_end - INTERNAL_TIME_STEPS);
51 for ( size_t ts = ts_start; ts < ts_end; ++ts)
52 {
53 sc_.accumulated_co2_emis += subdaily_co2_soil[ts] + subdaily_co2_plant[ts] + subdaily_co2_bubbling[ts] + subdaily_co2_water[ts];
54 sc_.accumulated_ch4_emis += subdaily_ch4_soil[ts] + subdaily_ch4_plant[ts] + subdaily_ch4_bubbling[ts] + subdaily_ch4_water[ts];
55 sc_.accumulated_n2o_emis += subdaily_n2o_soil[ts] + subdaily_n2o_plant[ts] + subdaily_n2o_bubbling[ts] + subdaily_n2o_water[ts];
56 sc_.accumulated_no_emis += subdaily_no_soil[ts] + subdaily_no_plant[ts] + subdaily_no_bubbling[ts] + subdaily_no_water[ts];
57 sc_.accumulated_nh3_emis += subdaily_nh3_soil[ts] + subdaily_nh3_plant[ts] + subdaily_nh3_bubbling[ts] + subdaily_nh3_water[ts];
58 sc_.accumulated_radon_emis += subdaily_radon_soil[ts] + subdaily_radon_plant[ts] + subdaily_radon_water[ts];
59
60 sc_.accumulated_ch4_leach += subdaily_ch4_leach[ts];
61 }
62
63 sc_.accumulated_co2_emis_auto += co2_auto_sl.sum();
64 sc_.accumulated_co2_emis_hetero += co2_hetero_sl.sum();
65
66 if (timemode_ == TMODE_SUBDAILY)
67 {
68 for ( PlantIterator vt = this->m_veg->begin(); vt != this->m_veg->end(); ++vt)
69 {
70 accumulated_n_to_living_plant_and_algae_from_extern_sl[0] += (*vt)->n2_fixation;
71 }
72 }
73 else
74 {
75 for ( PlantIterator vt = this->m_veg->begin(); vt != this->m_veg->end(); ++vt)
76 {
77 accumulated_n_to_living_plant_and_algae_from_extern_sl[0] += (*vt)->d_n2_fixation;
78 }
79 }
80
81 if ( timemode_ != TMODE_SUBDAILY || lclock()->is_position( TMODE_POST_DAILY))
82 {
83 /*************************/
84 /* Yearly rate variables */
85 /*************************/
86
87 sc_.accumulated_c_fix_algae += day_c_fix_algae;
88 sc_.accumulated_n_fix_algae += day_n_fix_algae;
89 }
90
92
93 return LDNDC_ERR_OK;
94}
lerr_t MeTrX_send_state()
Definition: soilchemistry-metrx-communicate.cpp:335

References MeTrX_send_state().

Referenced by solve().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ solve()

lerr_t ldndc::SoilChemistryMeTrX::solve ( )

Kicks off computation for one time step.

20{
21 if ( (lclock()->subday() == 1) || (timemode_ != TMODE_SUBDAILY))
22 {
23 subdaily_time_step_ = 0;
24 }
25
26 lerr_t rc = MeTrX_check_for_negative_value( "entry");
27 if ( rc) return LDNDC_ERR_FAIL;
28
30
31 rc = MeTrX_update();
32 if ( rc) return LDNDC_ERR_FAIL;
33
34 rc = MeTrX_spinup();
35 if ( rc) return LDNDC_ERR_FAIL;
36
37 rc = MeTrX_balance_check( 1);
38 if ( rc) return LDNDC_ERR_FAIL;
39
40 rc = MeTrX_physics();
41 if ( rc) return LDNDC_ERR_FAIL;
42
43 rc = MeTrX_fertilize();
44 if ( rc) return LDNDC_ERR_FAIL;
45
46 rc = MeTrX_irrigate();
47 if ( rc) return LDNDC_ERR_FAIL;
48
49 rc = MeTrX_manure();
50 if ( rc) return LDNDC_ERR_FAIL;
51
52 rc = MeTrX_till();
53 if ( rc) return LDNDC_ERR_FAIL;
54
56
57 for ( int ts = 0; ts < INTERNAL_TIME_STEPS; ++ts)
58 {
60
64 MeTrX_advection();
67
69
71
72 lerr_t rc_meta = MeTrX_metabolism();
73 if (rc_meta) { return rc_meta; }
74
75 lerr_t rc_pertub = MeTrX_pertubation();
76 if (rc_pertub) { return rc_pertub; }
77
80
85
90
94
96
99
102
103 subdaily_time_step_ += 1;
104 }
105
106 rc = MeTrX_balance_check( 2);
107 if ( rc) return LDNDC_ERR_FAIL;
108
111
112 rc = MeTrX_check_for_negative_value( "exit");
113 if ( rc) return LDNDC_ERR_FAIL;
114
115 return LDNDC_ERR_OK;
116}
lerr_t MeTrX_radon_source_sink()
Definition: soilchemistry-metrx-physics-chemistry.cpp:470
lerr_t MeTrX_spinup()
Definition: soilchemistry-metrx-spinup.cpp:68
lerr_t MeTrX_fertilize()
Definition: soilchemistry-metrx-management.cpp:33
lerr_t MeTrX_pertubation()
Definition: soilchemistry-metrx-transport.cpp:1638
void MeTrX_pH_calculation()
Definition: soilchemistry-metrx-physics-chemistry.cpp:621
void MeTrX_leaching()
Downwards transport of solutes, litter and humus with percolation water.
Definition: soilchemistry-metrx-transport.cpp:25
lerr_t MeTrX_write_output()
Definition: soilchemistry-metrx-output.cpp:16
lerr_t MeTrX_plant_respiration(int)
Updates o2 and co2 concentrations in soil layers. There is no o2 mass conservation guaranteed because...
Definition: soilchemistry-metrx-management.cpp:1093
lerr_t MeTrX_update()
Definition: soilchemistry-metrx-communicate.cpp:62
lerr_t MeTrX_freeze_thaw()
Definition: soilchemistry-metrx-physics-chemistry.cpp:409
void MeTrX_clay_nh4_equilibrium()
Definition: soilchemistry-metrx-physics-chemistry.cpp:95
lerr_t MeTrX_write_rates()
Definition: soilchemistry-metrx-integrate.cpp:19
lerr_t MeTrX_metabolism()
Definition: soilchemistry-metrx-microbial-dynamics.cpp:215
void MeTrX_soil_organic_matter_turnover()
lerr_t MeTrX_manure()
Definition: soilchemistry-metrx-management.cpp:318
lerr_t MeTrX_nitrogen_fertilizer_release()
Transforms nitrogen from slow release nitrogen fertilizer to nh4.
Definition: soilchemistry-metrx-management.cpp:1000
lerr_t MeTrX_till()
Definition: soilchemistry-metrx-management.cpp:756
void MeTrX_nh3_nh4_equilibrium()
Definition: soilchemistry-metrx-physics-chemistry.cpp:32
lerr_t MeTrX_check_for_negative_value(char const *)
iterates over complete soilchemistry state and checks for negative values
Definition: soilchemistry-metrx-balance-check.cpp:175
lerr_t MeTrX_reset()
Definition: soilchemistry-metrx-reset.cpp:185
lerr_t MeTrX_fragmentation()
Definition: soilchemistry-metrx-fragmentation.cpp:24
void MeTrX_urea_hydrolysis()
Definition: soilchemistry-metrx-management.cpp:933
void MeTrX_groundwater_access()
Definition: soilchemistry-metrx-transport.cpp:768

References MeTrX_algae_dynamics(), MeTrX_anaerobic_volume(), MeTrX_ch4_oxidation(), MeTrX_ch4_production(), MeTrX_check_for_negative_value(), MeTrX_chemodenitrification(), MeTrX_clay_nh4_equilibrium(), MeTrX_denitrification(), MeTrX_dissolution(), MeTrX_ebullition(), MeTrX_fermentation(), MeTrX_fertilize(), MeTrX_fragmentation(), MeTrX_freeze_thaw(), MeTrX_gas_diffusion(), MeTrX_groundwater_access(), MeTrX_iron_oxidation(), MeTrX_iron_reduction(), MeTrX_leaching(), MeTrX_liq_diffusion(), MeTrX_manure(), MeTrX_metabolism(), MeTrX_microbial_dynamics(), MeTrX_nh3_nh4_equilibrium(), MeTrX_nitrification(), MeTrX_nitrogen_fertilizer_release(), MeTrX_pertubation(), MeTrX_pH_calculation(), MeTrX_physics(), MeTrX_plant_respiration(), MeTrX_radon_source_sink(), MeTrX_reset(), MeTrX_soil_organic_matter_turnover(), MeTrX_spinup(), MeTrX_till(), MeTrX_update(), MeTrX_urea_hydrolysis(), MeTrX_write_output(), and MeTrX_write_rates().

Here is the call graph for this function:

Member Data Documentation

◆ C_SATURATION

const double ldndc::SoilChemistryMeTrX::C_SATURATION = 82.0 * cbm::KG_IN_G
staticprivate

C-saturation level for mineral associated cabon [kg(C):kg(silt+clay)-1]

Referenced by MeTrX_spinup().

◆ TNORM

const double ldndc::SoilChemistryMeTrX::TNORM = 293.2
staticprivate

Reference temperature [K]