Flow123d  last_with_con_2.0.0-4-g42e6930
soil_models.hh
Go to the documentation of this file.
1 /*
2  * File: hydro_functions.hh
3  * Author: jb
4  *
5  * Created on May 17, 2010, 1:52 PM
6  */
7 
8 #ifndef _HYDRO_FUNCTIONS_HH
9 #define _HYDRO_FUNCTIONS_HH
10 
11 
12 namespace fadbad {
13  template <class T> class B;
14 }
15 
16 // todo:
17 // objekt por SoilModel - jedna sada primarnich i pomocnych parametru
18 // konzistentni hydrologicke funkce
19 //
20 // potreboval bych mit vice modelu, z orezavanim i bez nej,
21 // orezavani zpusobuje velke residuum v miste nespojitosti derivace saturace
22 
23 // problem - jak pouzit funktory, FADBAD, aproximace a
24 // inverzi (inverze tlak v zav. na vlhkosti)
25 //
26 // podrobnejsi vyzkum ohledne hydrologickych funkci
27 // vodivost vyplyva s kapilarnich modelu (jak presne?)
28 // co vlhkost?
29 
30 /**
31  * One of possibly more classes specifying dependence of the relative conductivity and the relative water content on the
32  * pressure head. These functions (@p conductivity and @p water_content, respectively) are templates to allow evaluation of
33  * the derivatives through fadbad lib.
34  */
35 
36 struct SoilData {
37  double n; // power parameter
38  double alpha; // pressure head scaling
39  double Qr; // residual water content
40  double Qs; // saturated water content
41  double cut_fraction; // in (0,1), fraction of relative Q where to cut and rescale the retention curve
42  double Ks; // saturated conductivity
43 // double Kk; // conductivity at the cut point
44 };
45 
46 
47 /**
48  * Pure virtual interface, of all models.
49  */
51 public:
53  van_genuchten=0,
54  irmay=1
55  };
56 
58 
59  virtual void reset(SoilData soil)=0;
60 
61  virtual double conductivity( const double &phead) const =0;
62  virtual auto conductivity(const DiffDouble &p_head)->DiffDouble const =0;
63 
64  virtual double water_content( const double &phead) const =0;
65  virtual auto water_content(const DiffDouble &p_head)->DiffDouble const =0;
66 
67  virtual ~SoilModelBase() {};
68 };
69 
70 
71 template <class Model>
73 public:
74  // We assume that Model have method templates:
75  // template <class T> T conductivity_(const T &h) const;
76  // template <class T> T water_content_(const T &h) const;
77 
79 
80  void reset(SoilData data) override;
81 
82  double conductivity( const double &p_head) const override;
83  auto conductivity(const DiffDouble &p_head)->DiffDouble const override;
84 
85  double water_content( const double &p_head) const override;
86  auto water_content(const DiffDouble &p_head)->DiffDouble const override;
87 
89 
90 private:
91  Model model_;
92 };
93 
94 
95 
96 // ************************************** Internal model definitions
97 namespace internal {
98 
99 class VanGenuchten {
100 public:
101  VanGenuchten();
102 
103  void reset_(SoilData soil);
104 
105  template <class T>
106  T conductivity_(const T &h) const;
107 
108  template <class T>
109  T water_content_(const T &h) const;
110 
111 protected:
112 
113  template <class T> T Q_rel(const T &h) const;
114  template <class T> T Q_rel_inv(const T &q) const;
115 
116  // input parameters
118 
119  // constant conductivity parameters
120  double Bpar;
121  double Ppar;
123 
124  // aux values
125  double m;
126  double Qs_nc; // saturated value of continuation of cut water content function
127 
128 
129  double FFQr, FFQs;
130  double Hs;
131 
132 };
133 
134 
135 
136 class Irmay : public VanGenuchten {
137 public:
138  Irmay();
139 
140  template <class T>
141  T conductivity_(const T &h) const;
142 };
143 
144 } // close namespace internal
145 
146 
149 
150 
151 
152 
153 
154 
155 
156 
157 
158 
159 /*
160 
161 //FK-------------------------------------------------------------
162 template <class T>
163 class FK //FK - hydraulic conductivity function
164 {
165 private:
166 // function parameters
167 static const double Bpar; // = 0.5;
168 static const double PPar; // = 2;
169 
170 HydrologyParams par;
171 
172 // auxiliary parameters
173 double Qa,Qm,Qk,m,Hr,Hk,Hs,C1Qee,C2Qee,Qeer,Qees,Qeek;
174 public:
175  FK(const HydrologyParams &par);
176  T operator()(const T& h);
177 };
178 
179 template <class T> const double FK<T>::Bpar =0.5;
180 template <class T> const double FK<T>::PPar =2;
181 
182 template <class T>
183 FK<T> :: FK(const HydrologyParams &par)
184 : par(par)
185 {
186 
187  m = 1-1/par.n;
188 
189  Qa=par.Qr;
190  Qm=par.Qs / par.cut_fraction;
191  //Qk=0.99 * par.Qs;
192  Qk=par.Qs;
193  C1Qee = 1/(Qm - Qa);
194  C2Qee = -Qa/(Qm - Qa);
195 // if (par.cut_fraction >0.9999) {
196 // Hr=-1000;
197 // Hk=Hs=0;
198 // return;
199 // }
200  // fraction =1
201  Qees = C1Qee * par.Qs + C2Qee; // 1
202  Qeek = min(C1Qee * Qk + C2Qee, Qees); // 1
203  Qeer = min(C1Qee * par.Qr + C2Qee, Qeek); // 0
204 
205  Hr = -1/par.alfa*pow(pow(Qeer,-1/m)-1,1/par.n); //
206  Hs = -1/par.alfa*pow(pow(Qees,-1/m)-1,1/par.n);
207  Hk = -1/par.alfa*pow(pow(Qeek,-1/m)-1,1/par.n);
208 
209  cout << "K: Hr, Hs, Hk:" << Hr << " " << Hs << " " << Hk << endl;
210 }
211 
212 template <class T>
213 T FK<T> :: operator()(const T& h)
214 {
215  T Kr,FFQr,FFQ,FFQk,Qee,Qe,Qek,C1Qe,C2Qe,Q;
216 
217  if (h < Hr) return par.Ks*(1E-200); // numericaly zero Kr
218  else
219  if (h < Hk) {
220  Q = Qa + (Qm - Qa)*pow((1 + pow(-par.alfa*h,par.n)),-m);
221  Qee = C1Qee*Q + C2Qee;
222  FFQr = pow(1 - pow(Qeer,1/m),m);
223  FFQ = pow(1 - pow(Qee,1/m),m);
224  FFQk = pow(1 - pow(Qeek,1/m),m);
225  C1Qe = 1/(par.Qs - par.Qr);
226  C2Qe = -par.Qr/(par.Qs - par.Qr);
227  Qe = C1Qe*Q + C2Qe;
228  Qek = C1Qe*Qk + C2Qe;
229  Kr = pow(Qe/Qek,Bpar)*pow((FFQr - FFQ)/(FFQr - FFQk),PPar) * par.Kk/par.Ks;
230  return ( max<T>(par.Ks*Kr,par.Ks*(1E-10)) );
231  }
232  else if(h <= Hs)
233  {
234  Kr = (1-par.Kk/par.Ks)/(Hs-Hk)*(h-Hs) + 1;
235  return ( par.Ks*Kr );
236  }
237  else return par.Ks;
238 }
239 
240 
241 //FQ--------------------------------------------------------------
242 template <class T>
243 class FQ //FQ - water saturation function
244 {
245 HydrologyParams par;
246 // auxiliary parameters
247 double m, Qeer,Qees,Hr,Hs, Qa, Qm;
248 public:
249  FQ(const HydrologyParams &par);
250  T operator()(const T& h);
251 };
252 
253 template <class T>
254 FQ<T>::FQ(const HydrologyParams &par)
255 : par(par)
256 {
257  m = 1 - 1 / par.n;
258 
259 // if (par.cut_fraction >0.9999) {
260 // Hr=-1000;
261 // Hs=0;
262 // return;
263 // }
264  Qm=par.Qs / par.cut_fraction;
265  Qa=par.Qr;
266 
267  Qeer = (par.Qr - Qa)/ (Qm - Qa);
268  Qees = (par.Qs - Qa)/ (Qm - Qa);
269  Hr = -1 / par.alfa * pow( pow(Qeer,-1/m)-1, 1/par.n);
270  Hs = -1 / par.alfa * pow( pow(Qees,-1/m)-1, 1/par.n);
271 
272  cout << "Q: Hr, Hs:" << Hr << " " << Hs << " " << endl;
273 }
274 
275 
276 template <class T>
277 T FQ<T>::operator()(const T& h)
278 {
279  T Qee;
280 
281  if (h < Hr) return par.Qr;
282  else if (h < Hs) {
283  Qee = pow( 1 + pow(-par.alfa * h, par.n), -m);
284  return Qa + (Qm - Qa) * Qee;
285  }
286  else return par.Qs;
287 
288 }
289 
290 //FC--------------------------------------------------------------
291 template <class T>
292 class FC //FC - water capacity function FQ derivative
293 {
294 HydrologyParams par;
295 // auxiliary parameters
296 double m, C1Qee,C2Qee,Qeer,Qees,Hr,Hs, Qa, Qm;
297 public:
298  FC(const HydrologyParams &par);
299  T operator()(const T& h);
300 };
301 
302 template <class T>
303 FC<T>::FC(const HydrologyParams &par)
304 : par(par)
305 {
306  m = 1 - 1 / par.n;
307  Qm=par.Qs / par.cut_fraction;
308  Qa=par.Qr;
309 
310  C1Qee = 1/(Qm - Qa);
311  C2Qee = -Qa/(Qm - Qa);
312  Qeer = C1Qee * par.Qr + C2Qee;
313  Qees = C1Qee * par.Qs + C2Qee;
314  Hr = -1 / par.alfa * pow( pow(Qeer,-1/m)-1, 1/par.n);
315  Hs = -1 / par.alfa * pow( pow(Qees,-1/m)-1, 1/par.n);
316 }
317 
318 
319 template <class T>
320 T FC<T>::operator()(const T& h)
321 {
322  T C1;
323 
324  if (h <= Hr)
325  return 0.0;
326  else if ( h < Hs ) {
327  C1=pow( 1 + pow( -par.alfa * h, par.n), -m-1);
328  return (Qm - Qa) * m * par.n * pow(par.alfa, par.n)*pow(-h, par.n-1)*C1;
329  }
330  else
331  return 0.0;
332 }
333 
334 
335 ! ************************************************************************
336 ! FH - inverse water saturation function
337 ! **************************************
338 real pure function FH_4(h,Matr)
339 implicit none
340 integer,INTENT(IN) :: Matr
341 real, INTENT(IN) :: h
342  FH_4=FH_8(DBLE(h),Matr)
343 end function FH_4
344 
345 double precision pure function FH_8(Qe,Matr)
346 implicit none
347 integer, INTENT(IN) :: Matr
348 double precision,INTENT(IN) :: Qe
349 double precision :: n,m,Qr,Qs,Qa,Qm,Alfa,Q,Qee
350 
351  Qr=par(1,Matr)
352  Qs=par(2,Matr)
353  Qa=par(3,Matr)
354  Qm=par(4,Matr)
355  Alfa=par(5,Matr)
356  n=par(6,Matr)
357  m=1-1/n
358  Q=Qr+(Qs-Qr)*Qe
359  Qee=dmax1((Q-Qa)/(Qm-Qa),1d-3)
360  Qee=dmin1(Qee,1-1d-15)
361  FH_8=-1/Alfa*(Qee**(-1/m)-1)**(1/n)
362 end function FH_8
363 */
364 
365 // Conductivity for analytical solution
366 /*
367 class HydroModel_analytical
368 {
369 public:
370  HydroModel_analytical(ParameterHandler &prm) {};
371 
372  /// Maximum point of capacity. (computed numericaly from eq. atan(x)*2x=1 )
373  inline double cap_arg_max() const { return -0.765378926665788882857; }
374 
375  template <class T>
376  T FK(const T &h) const
377  {
378  if (h>=0.0) return ( 2.0 );
379  return ( 2.0 / (1+h*h) );
380  }
381 
382  template <class T>
383  T FQ(const T &h) const
384  {
385  static T pi_half =std::atan(1.0)*2;
386  if (h>=0.0) return ( 2.0*pi_half*pi_half );
387  T a_tan = atan(h);
388  return ( 2*pi_half*pi_half - a_tan*a_tan );
389  }
390 private:
391  double arg_cap_max;
392 };
393 
394 
395 class HydroModel_linear
396 {
397  HydroModel_linear(ParameterHandler &prm) {};
398 
399 public:
400  template <class T>
401  T FK(const T &h) const {
402  return 1.0;
403  }
404 
405  template <class T>
406  T FQ(const T &h) const {
407  return h;
408  }
409 };
410 
411 */
412 #endif /* _HYDRO_FUNCTIONS_HH */
413 
virtual ~SoilModelBase()
Definition: soil_models.hh:67
double cut_fraction
Definition: soil_models.hh:41
double alpha
Definition: soil_models.hh:38
fadbad::B< double > DiffDouble
Definition: soil_models.hh:57
double Qr
Definition: soil_models.hh:39
double Qs
Definition: soil_models.hh:40
double Ks
Definition: soil_models.hh:42
SoilModelImplBase< internal::Irmay > SoilModel_Irmay
Definition: soil_models.hh:148
SoilModelBase::DiffDouble DiffDouble
Definition: soil_models.hh:78
SoilModelImplBase< internal::VanGenuchten > SoilModel_VanGenuchten
Definition: soil_models.hh:147
double n
Definition: soil_models.hh:37