![]() |
MechSys
1.0
Computing library for simulations in continuum and discrete mechanics
|
00001 /************************************************************************ 00002 * MechSys - Open Library for Mechanical Systems * 00003 * Copyright (C) 2005 Dorival M. Pedroso, Raúl D. D. Farfan * 00004 * * 00005 * This program is free software: you can redistribute it and/or modify * 00006 * it under the terms of the GNU General Public License as published by * 00007 * the Free Software Foundation, either version 3 of the License, or * 00008 * any later version. * 00009 * * 00010 * This program is distributed in the hope that it will be useful, * 00011 * but WITHOUT ANY WARRANTY; without even the implied warranty of * 00012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * 00013 * GNU General Public License for more details. * 00014 * * 00015 * You should have received a copy of the GNU General Public License * 00016 * along with this program. If not, see <http://www.gnu.org/licenses/> * 00017 ************************************************************************/ 00018 00019 #ifndef MECHSYS_DRIVER_H 00020 #define MECHSYS_DRIVER_H 00021 00022 // Std Lib 00023 #include <cmath> 00024 #include <sstream> 00025 00026 // MechSys 00027 #include <mechsys/models/model.h> 00028 #include <mechsys/numerical/odesolver.h> 00029 00030 using std::cout; 00031 using std::endl; 00032 00033 class Driver 00034 { 00035 public: 00036 // Constructor & Destructor 00037 Driver (String const & ModelName, SDPair const & Prms, SDPair const & Inis); 00038 ~Driver (); 00039 00040 // Methods 00041 void Update (); 00042 00043 // Data to be set before calling update methods 00044 Array<bool> PrescDEps; 00045 Vec_t DEps; 00046 Vec_t DSig; 00047 00048 // Data 00049 Model * Mdl; 00050 EquilibState * Sta; 00051 double Tol; 00052 bool CheckModelTgIncs; 00053 String RKScheme; 00054 double RKStol; 00055 Vec_t DIvs; 00056 int GivenIncsCase; 00057 bool Linear; 00058 00059 private: 00060 // Callbacks 00061 int _RK_3Comps (double t, double const Y[], double dYdt[]); 00062 EquilibState * _RK_state; 00063 Vec_t _RK_EpsIni; 00064 Vec_t _RK_SigIni; 00065 double _tmp_dYdt[3]; 00066 }; 00067 00068 00070 00071 00072 inline Driver::Driver (String const & ModelName, SDPair const & Prms, SDPair const & Inis) 00073 : Tol(DBL_EPSILON), CheckModelTgIncs(true), RKScheme("RKF45"), RKStol(1.0e-5), GivenIncsCase(-1), 00074 Linear(false) 00075 { 00076 Mdl = AllocModel (ModelName, 3, Prms, /*AnotherMdl*/NULL); 00077 Sta = new EquilibState (3); 00078 Mdl->InitIvs (Inis, Sta); 00079 00080 PrescDEps.Resize (6); 00081 DEps.change_dim (6); 00082 DSig.change_dim (6); 00083 if (Mdl->NIvs>0) DIvs.change_dim (Mdl->NIvs); 00084 00085 _RK_state = new EquilibState (3); 00086 _RK_EpsIni.change_dim (6); 00087 _RK_SigIni.change_dim (6); 00088 } 00089 00090 inline Driver::~Driver () 00091 { 00092 delete Mdl; 00093 delete Sta; 00094 delete _RK_state; 00095 } 00096 00097 inline void Driver::Update () 00098 { 00099 // ODE solver 00100 Numerical::ODESolver<Driver> ode(this, &Driver::_RK_3Comps, /*neq*/3+Mdl->NIvs, RKScheme.CStr(), RKStol); 00101 00102 // initial values 00103 ode.t = 0.0; 00104 if ( PrescDEps[0] && PrescDEps[1] && PrescDEps[2]) // 1) all DEps are given 00105 { 00106 GivenIncsCase = 1; 00107 ode.Y[0] = Sta->Sig(0); 00108 ode.Y[1] = Sta->Sig(1); 00109 ode.Y[2] = Sta->Sig(2); 00110 } 00111 else if (!PrescDEps[0] && !PrescDEps[1] && !PrescDEps[2]) // 2) all DSig are given 00112 { 00113 GivenIncsCase = 2; 00114 ode.Y[0] = Sta->Eps(0); 00115 ode.Y[1] = Sta->Eps(1); 00116 ode.Y[2] = Sta->Eps(2); 00117 } 00118 else if ( PrescDEps[0] && !PrescDEps[1] && !PrescDEps[2]) // 3) DEps[0], DSig[1], and DSig[2] are given 00119 { 00120 GivenIncsCase = 3; 00121 ode.Y[0] = Sta->Sig(0); 00122 ode.Y[1] = Sta->Eps(1); 00123 ode.Y[2] = Sta->Eps(2); 00124 } 00125 else if (!PrescDEps[0] && PrescDEps[1] && !PrescDEps[2]) // 4) DSig[0], DEps[1], and DSig[2] are given 00126 { 00127 GivenIncsCase = 4; 00128 ode.Y[0] = Sta->Eps(0); 00129 ode.Y[1] = Sta->Sig(1); 00130 ode.Y[2] = Sta->Eps(2); 00131 } 00132 else if (!PrescDEps[0] && !PrescDEps[1] && PrescDEps[2]) // 5) DSig[0], DSig[1], and DEps[2] are given 00133 { 00134 GivenIncsCase = 5; 00135 ode.Y[0] = Sta->Eps(0); 00136 ode.Y[1] = Sta->Eps(1); 00137 ode.Y[2] = Sta->Sig(2); 00138 } 00139 else if ( PrescDEps[0] && PrescDEps[1] && !PrescDEps[2]) // 6) DEps[0], DEps[1], and DSig[2] are given 00140 { 00141 GivenIncsCase = 6; 00142 ode.Y[0] = Sta->Sig(0); 00143 ode.Y[1] = Sta->Sig(1); 00144 ode.Y[2] = Sta->Eps(2); 00145 } 00146 else if ( PrescDEps[0] && !PrescDEps[1] && PrescDEps[2]) // 7) DEps[0], DSig[1], and DEps[2] are given 00147 { 00148 GivenIncsCase = 7; 00149 ode.Y[0] = Sta->Sig(0); 00150 ode.Y[1] = Sta->Eps(1); 00151 ode.Y[2] = Sta->Sig(2); 00152 } 00153 else if (!PrescDEps[0] && PrescDEps[1] && PrescDEps[2]) // 8) DSig[0], DEps[1], and DEps[2] are given 00154 { 00155 GivenIncsCase = 8; 00156 ode.Y[0] = Sta->Eps(0); 00157 ode.Y[1] = Sta->Sig(1); 00158 ode.Y[2] = Sta->Sig(2); 00159 } 00160 else throw new Fatal("Driver::Update: __internal_error__: combination of prescribed DEps is invalid"); 00161 00162 // initial internal values 00163 for (size_t i=0; i<Mdl->NIvs; ++i) ode.Y[3+i] = Sta->Ivs(i); 00164 00165 // set variables for _RK_3Comps 00166 _RK_EpsIni = Sta->Eps; 00167 _RK_SigIni = Sta->Sig; 00168 _RK_state->Eps(3) = 0.0; 00169 _RK_state->Eps(4) = 0.0; 00170 _RK_state->Eps(5) = 0.0; 00171 _RK_state->Sig(3) = 0.0; 00172 _RK_state->Sig(4) = 0.0; 00173 _RK_state->Sig(5) = 0.0; 00174 if (Mdl->NIvs>0) _RK_state->Ivs.change_dim (Mdl->NIvs); 00175 00176 // loading condition 00177 _RK_3Comps (0.0, ode.Y, _tmp_dYdt); 00178 if (GivenIncsCase==1) // 1) all DEps are given 00179 { 00180 DSig(0) = _tmp_dYdt[0]; // * 1.0 00181 DSig(1) = _tmp_dYdt[1]; 00182 DSig(2) = _tmp_dYdt[2]; 00183 } 00184 else if (GivenIncsCase==2) // 2) all DSig are given 00185 { 00186 DEps(0) = _tmp_dYdt[0]; 00187 DEps(1) = _tmp_dYdt[1]; 00188 DEps(2) = _tmp_dYdt[2]; 00189 } 00190 else if (GivenIncsCase==3) // 3) DEps[0], DSig[1], and DSig[2] are given 00191 { 00192 DSig(0) = _tmp_dYdt[0]; 00193 DEps(1) = _tmp_dYdt[1]; 00194 DEps(2) = _tmp_dYdt[2]; 00195 } 00196 else if (GivenIncsCase==4) // 4) DSig[0], DEps[1], and DSig[2] are given 00197 { 00198 DEps(0) = _tmp_dYdt[0]; 00199 DSig(1) = _tmp_dYdt[1]; 00200 DEps(2) = _tmp_dYdt[2]; 00201 } 00202 else if (GivenIncsCase==5) // 5) DSig[0], DSig[1], and DEps[2] are given 00203 { 00204 DEps(0) = _tmp_dYdt[0]; 00205 DEps(1) = _tmp_dYdt[1]; 00206 DSig(2) = _tmp_dYdt[2]; 00207 } 00208 else if (GivenIncsCase==6) // 6) DEps[0], DEps[1], and DSig[2] are given 00209 { 00210 DSig(0) = _tmp_dYdt[0]; 00211 DSig(1) = _tmp_dYdt[1]; 00212 DEps(2) = _tmp_dYdt[2]; 00213 } 00214 else if (GivenIncsCase==7) // 7) DEps[0], DSig[1], and DEps[2] are given 00215 { 00216 DSig(0) = _tmp_dYdt[0]; 00217 DEps(1) = _tmp_dYdt[1]; 00218 DSig(2) = _tmp_dYdt[2]; 00219 } 00220 else if (GivenIncsCase==6) // 8) DSig[0], DEps[1], and DEps[2] are given 00221 { 00222 DEps(0) = _tmp_dYdt[0]; 00223 DSig(1) = _tmp_dYdt[1]; 00224 DSig(2) = _tmp_dYdt[2]; 00225 } 00226 double aint = -1.0; // no intersection 00227 Sta->Ldg = Mdl->LoadCond (Sta, DEps, aint); // returns true if there is loading (also when there is intersection) 00228 _RK_state->Ldg = Sta->Ldg; 00229 00230 00231 cout << "case = " << GivenIncsCase << endl; 00232 00233 00234 // solve 00235 if (Linear) 00236 { 00237 Sta->Sig += DSig; 00238 Sta->Eps += DEps; 00239 return; 00240 } 00241 else ode.Evolve (/*tf*/1.0); 00242 00243 // results 00244 if (GivenIncsCase==1) // 1) all DEps are given 00245 { 00246 Sta->Sig(0) = ode.Y[0]; 00247 Sta->Sig(1) = ode.Y[1]; 00248 Sta->Sig(2) = ode.Y[2]; 00249 } 00250 else if (GivenIncsCase==2) // 2) all DSig are given 00251 { 00252 Sta->Eps(0) = ode.Y[0]; 00253 Sta->Eps(1) = ode.Y[1]; 00254 Sta->Eps(2) = ode.Y[2]; 00255 } 00256 else if (GivenIncsCase==3) // 3) DEps[0], DSig[1], and DSig[2] are given 00257 { 00258 Sta->Sig(0) = ode.Y[0]; 00259 Sta->Eps(1) = ode.Y[1]; 00260 Sta->Eps(2) = ode.Y[2]; 00261 } 00262 else if (GivenIncsCase==4) // 4) DSig[0], DEps[1], and DSig[2] are given 00263 { 00264 Sta->Eps(0) = ode.Y[0]; 00265 Sta->Sig(1) = ode.Y[1]; 00266 Sta->Eps(2) = ode.Y[2]; 00267 } 00268 else if (GivenIncsCase==5) // 5) DSig[0], DSig[1], and DEps[2] are given 00269 { 00270 Sta->Eps(0) = ode.Y[0]; 00271 Sta->Eps(1) = ode.Y[1]; 00272 Sta->Sig(2) = ode.Y[2]; 00273 } 00274 else if (GivenIncsCase==6) // 6) DEps[0], DEps[1], and DSig[2] are given 00275 { 00276 Sta->Sig(0) = ode.Y[0]; 00277 Sta->Sig(1) = ode.Y[1]; 00278 Sta->Eps(2) = ode.Y[2]; 00279 } 00280 else if (GivenIncsCase==7) // 7) DEps[0], DSig[1], and DEps[2] are given 00281 { 00282 Sta->Sig(0) = ode.Y[0]; 00283 Sta->Eps(1) = ode.Y[1]; 00284 Sta->Sig(2) = ode.Y[2]; 00285 } 00286 else if (GivenIncsCase==6) // 8) DSig[0], DEps[1], and DEps[2] are given 00287 { 00288 Sta->Eps(0) = ode.Y[0]; 00289 Sta->Sig(1) = ode.Y[1]; 00290 Sta->Sig(2) = ode.Y[2]; 00291 } 00292 00293 // internal values at time t 00294 for (size_t i=0; i<Mdl->NIvs; ++i) Sta->Ivs(i) = ode.Y[3+i]; 00295 } 00296 00297 inline int Driver::_RK_3Comps (double t, double const Y[], double dYdt[]) 00298 { 00299 // state at time t 00300 if (GivenIncsCase==1) // 1) all DEps are given 00301 { 00302 _RK_state->Eps(0) = _RK_EpsIni(0) + t * DEps(0); 00303 _RK_state->Eps(1) = _RK_EpsIni(1) + t * DEps(1); 00304 _RK_state->Eps(2) = _RK_EpsIni(2) + t * DEps(2); 00305 _RK_state->Sig(0) = Y[0]; 00306 _RK_state->Sig(1) = Y[1]; 00307 _RK_state->Sig(2) = Y[2]; 00308 } 00309 else if (GivenIncsCase==2) // 2) all DSig are given 00310 { 00311 _RK_state->Eps(0) = Y[0]; 00312 _RK_state->Eps(1) = Y[1]; 00313 _RK_state->Eps(2) = Y[2]; 00314 _RK_state->Sig(0) = _RK_SigIni(0) + t * DSig(0); 00315 _RK_state->Sig(1) = _RK_SigIni(1) + t * DSig(1); 00316 _RK_state->Sig(2) = _RK_SigIni(2) + t * DSig(2); 00317 } 00318 else if (GivenIncsCase==3) // 3) DEps[0], DSig[1], and DSig[2] are given 00319 { 00320 _RK_state->Eps(0) = _RK_EpsIni(0) + t * DEps(0); 00321 _RK_state->Eps(1) = Y[1]; 00322 _RK_state->Eps(2) = Y[2]; 00323 _RK_state->Sig(0) = Y[0]; 00324 _RK_state->Sig(1) = _RK_SigIni(1) + t * DSig(1); 00325 _RK_state->Sig(2) = _RK_SigIni(2) + t * DSig(2); 00326 } 00327 else if (GivenIncsCase==4) // 4) DSig[0], DEps[1], and DSig[2] are given 00328 { 00329 _RK_state->Eps(0) = Y[0]; 00330 _RK_state->Eps(1) = _RK_EpsIni(1) + t * DEps(1); 00331 _RK_state->Eps(2) = Y[2]; 00332 _RK_state->Sig(0) = _RK_SigIni(0) + t * DSig(0); 00333 _RK_state->Sig(1) = Y[1]; 00334 _RK_state->Sig(2) = _RK_SigIni(2) + t * DSig(2); 00335 } 00336 else if (GivenIncsCase==5) // 5) DSig[0], DSig[1], and DEps[2] are given 00337 { 00338 _RK_state->Eps(0) = Y[0]; 00339 _RK_state->Eps(1) = Y[1]; 00340 _RK_state->Eps(2) = _RK_EpsIni(2) + t * DEps(2); 00341 _RK_state->Sig(0) = _RK_SigIni(0) + t * DSig(0); 00342 _RK_state->Sig(1) = _RK_SigIni(1) + t * DSig(1); 00343 _RK_state->Sig(2) = Y[2]; 00344 } 00345 else if (GivenIncsCase==6) // 6) DEps[0], DEps[1], and DSig[2] are given 00346 { 00347 _RK_state->Eps(0) = _RK_EpsIni(0) + t * DEps(0); 00348 _RK_state->Eps(1) = _RK_EpsIni(1) + t * DEps(1); 00349 _RK_state->Eps(2) = Y[2]; 00350 _RK_state->Sig(0) = Y[0]; 00351 _RK_state->Sig(1) = Y[1]; 00352 _RK_state->Sig(2) = _RK_SigIni(2) + t * DSig(2); 00353 } 00354 else if (GivenIncsCase==7) // 7) DEps[0], DSig[1], and DEps[2] are given 00355 { 00356 _RK_state->Eps(0) = _RK_EpsIni(0) + t * DEps(0); 00357 _RK_state->Eps(1) = Y[1]; 00358 _RK_state->Eps(2) = _RK_EpsIni(2) + t * DEps(2); 00359 _RK_state->Sig(0) = Y[0]; 00360 _RK_state->Sig(1) = _RK_SigIni(1) + t * DSig(1); 00361 _RK_state->Sig(2) = Y[2]; 00362 } 00363 else if (GivenIncsCase==6) // 8) DSig[0], DEps[1], and DEps[2] are given 00364 { 00365 _RK_state->Eps(0) = Y[0]; 00366 _RK_state->Eps(1) = _RK_EpsIni(1) + t * DEps(1); 00367 _RK_state->Eps(2) = _RK_EpsIni(2) + t * DEps(2); 00368 _RK_state->Sig(0) = _RK_SigIni(0) + t * DSig(0); 00369 _RK_state->Sig(1) = Y[1]; 00370 _RK_state->Sig(2) = Y[2]; 00371 } 00372 00373 // internal values at time t 00374 for (size_t i=0; i<Mdl->NIvs; ++i) _RK_state->Ivs(i) = Y[3+i]; 00375 00376 // stiffness 00377 Mat_t D; 00378 Mdl->Stiffness (_RK_state, D); 00379 00380 // stress/strain increments 00381 if (GivenIncsCase==1) // 1) all DEps are given 00382 { 00383 dYdt[0] = DSig(0) = D(0,0)*DEps(0) + D(0,1)*DEps(1) + D(0,2)*DEps(2); 00384 dYdt[1] = DSig(1) = D(1,0)*DEps(0) + D(1,1)*DEps(1) + D(1,2)*DEps(2); 00385 dYdt[2] = DSig(2) = D(2,0)*DEps(0) + D(2,1)*DEps(1) + D(2,2)*DEps(2); 00386 } 00387 else if (GivenIncsCase==2) // 2) all DSig are given 00388 { 00389 double den2 = D(0,0)*(D(1,2)*D(2,1)-D(1,1)*D(2,2))+D(0,1)*(D(1,0)*D(2,2)-D(1,2)*D(2,0))+D(0,2)*(D(1,1)*D(2,0)-D(1,0)*D(2,1)); 00390 if (fabs(den2)<Tol) throw new Fatal("Driver::TgIncs3Comps: division by null denominator (%g)",den2); 00391 dYdt[0] = DEps(0) = (DSig(0)*(D(1,2)*D(2,1)-D(1,1)*D(2,2))+D(0,1)*(DSig(1)*D(2,2)-D(1,2)*DSig(2))+D(0,2)*(D(1,1)*DSig(2)-DSig(1)*D(2,1)))/den2; 00392 dYdt[1] = DEps(1) = -(DSig(0)*(D(1,2)*D(2,0)-D(1,0)*D(2,2))+D(0,0)*(DSig(1)*D(2,2)-D(1,2)*DSig(2))+D(0,2)*(D(1,0)*DSig(2)-DSig(1)*D(2,0)))/den2; 00393 dYdt[2] = DEps(2) = (DSig(0)*(D(1,1)*D(2,0)-D(1,0)*D(2,1))+D(0,0)*(DSig(1)*D(2,1)-D(1,1)*DSig(2))+D(0,1)*(D(1,0)*DSig(2)-DSig(1)*D(2,0)))/den2; 00394 } 00395 else if (GivenIncsCase==3) // 3) DEps[0], DSig[1], and DSig[2] are given 00396 { 00397 double den3 = D(1,2)*D(2,1)-D(1,1)*D(2,2); 00398 if (fabs(den3)<Tol) throw new Fatal("Driver::TgIncs3Comps: division by null denominator (%g)",den3); 00399 dYdt[0] = DSig(0) = (DEps(0)*D(0,0)*den3+D(0,1)*(DEps(0)*(D(1,0)*D(2,2)-D(1,2)*D(2,0))-DSig(1)*D(2,2)+D(1,2)*DSig(2))+D(0,2)*(DEps(0)*(D(1,1)*D(2,0)-D(1,0)*D(2,1))+DSig(1)*D(2,1)-D(1,1)*DSig(2)))/den3; 00400 dYdt[1] = DEps(1) = -(DEps(0)*(D(1,2)*D(2,0)-D(1,0)*D(2,2))+DSig(1)*D(2,2)-D(1,2)*DSig(2))/den3; 00401 dYdt[2] = DEps(2) = (DEps(0)*(D(1,1)*D(2,0)-D(1,0)*D(2,1))+DSig(1)*D(2,1)-D(1,1)*DSig(2))/den3; 00402 } 00403 else if (GivenIncsCase==4) // 4) DSig[0], DEps[1], and DSig[2] are given 00404 { 00405 double den4 = D(0,2)*D(2,0)-D(0,0)*D(2,2); 00406 if (fabs(den4)<Tol) throw new Fatal("Driver::TgIncs3Comps: division by null denominator (%g)",den4); 00407 dYdt[0] = DEps(0) = -(DEps(1)*(D(0,2)*D(2,1)-D(0,1)*D(2,2))+DSig(0)*D(2,2)-D(0,2)*DSig(2))/den4; 00408 dYdt[1] = DSig(1) = (DEps(1)*(D(0,0)*(D(1,2)*D(2,1)-D(1,1)*D(2,2))+D(0,1)*(D(1,0)*D(2,2)-D(1,2)*D(2,0))+D(0,2)*(D(1,1)*D(2,0)-D(1,0)*D(2,1)))+DSig(0)*(D(1,2)*D(2,0)-D(1,0)*D(2,2))-D(0,0)*D(1,2)*DSig(2)+D(0,2)*D(1,0)*DSig(2))/den4; 00409 dYdt[2] = DEps(2) = -(DEps(1)*(D(0,1)*D(2,0)-D(0,0)*D(2,1))-DSig(0)*D(2,0)+D(0,0)*DSig(2))/den4; 00410 } 00411 else if (GivenIncsCase==5) // 5) DSig[0], DSig[1], and DEps[2] are given 00412 { 00413 double den5 = D(0,1)*D(1,0)-D(0,0)*D(1,1); 00414 if (fabs(den5)<Tol) throw new Fatal("Driver::TgIncs3Comps: division by null denominator (%g)",den5); 00415 dYdt[0] = DEps(0) = ((D(0,2)*D(1,1)-D(0,1)*D(1,2))*DEps(2)-DSig(0)*D(1,1)+D(0,1)*DSig(1))/den5; 00416 dYdt[1] = DEps(1) = -((D(0,2)*D(1,0)-D(0,0)*D(1,2))*DEps(2)-DSig(0)*D(1,0)+D(0,0)*DSig(1))/den5; 00417 dYdt[2] = DSig(2) = (DEps(2)*(D(0,0)*(D(1,2)*D(2,1)-D(1,1)*D(2,2))+D(0,1)*(D(1,0)*D(2,2)-D(1,2)*D(2,0))+D(0,2)*(D(1,1)*D(2,0)-D(1,0)*D(2,1)))+DSig(0)*(D(1,0)*D(2,1)-D(1,1)*D(2,0))-D(0,0)*DSig(1)*D(2,1)+D(0,1)*DSig(1)*D(2,0))/den5; 00418 } 00419 else if (GivenIncsCase==6) // 6) DEps[0], DEps[1], and DSig[2] are given 00420 { 00421 if (fabs(D(2,2))<Tol) throw new Fatal("Driver::TgIncs3Comps: division by null denominator (%g)",D(2,2)); 00422 dYdt[0] = DSig(0) = -(DEps(1)*(D(0,2)*D(2,1)-D(0,1)*D(2,2))-DEps(0)*D(0,0)*D(2,2)+D(0,2)*(DEps(0)*D(2,0)-DSig(2)))/D(2,2); 00423 dYdt[1] = DSig(1) = -(DEps(1)*(D(1,2)*D(2,1)-D(1,1)*D(2,2))+DEps(0)*(D(1,2)*D(2,0)-D(1,0)*D(2,2))-D(1,2)*DSig(2))/D(2,2); 00424 dYdt[2] = DEps(2) = -(DEps(1)*D(2,1)+DEps(0)*D(2,0)-DSig(2))/D(2,2); 00425 } 00426 else if (GivenIncsCase==7) // 7) DEps[0], DSig[1], and DEps[2] are given 00427 { 00428 if (fabs(D(1,1))<Tol) throw new Fatal("Driver::TgIncs3Comps: division by null denominator (%g)",D(1,1)); 00429 dYdt[0] = DSig(0) = ((D(0,2)*D(1,1)-D(0,1)*D(1,2))*DEps(2)+DEps(0)*D(0,0)*D(1,1)+D(0,1)*(DSig(1)-DEps(0)*D(1,0)))/D(1,1); 00430 dYdt[1] = DEps(1) = -(D(1,2)*DEps(2)+DEps(0)*D(1,0)-DSig(1))/D(1,1); 00431 dYdt[2] = DSig(2) = -(DEps(2)*(D(1,2)*D(2,1)-D(1,1)*D(2,2))+DEps(0)*(D(1,0)*D(2,1)-D(1,1)*D(2,0))-DSig(1)*D(2,1))/D(1,1); 00432 } 00433 else if (GivenIncsCase==8) // 8) DSig[0], DEps[1], and DEps[2] are given 00434 { 00435 if (fabs(D(0,0))<Tol) throw new Fatal("Driver::TgIncs3Comps: division by null denominator (%g)",D(0,0)); 00436 dYdt[0] = DEps(0) = -(D(0,2)*DEps(2)+D(0,1)*DEps(1)-DSig(0))/D(0,0); 00437 dYdt[1] = DSig(1) = -((D(0,2)*D(1,0)-D(0,0)*D(1,2))*DEps(2)+DEps(1)*(D(0,1)*D(1,0)-D(0,0)*D(1,1))-DSig(0)*D(1,0))/D(0,0); 00438 dYdt[2] = DSig(2) = -(DEps(2)*(D(0,2)*D(2,0)-D(0,0)*D(2,2))+DEps(1)*(D(0,1)*D(2,0)-D(0,0)*D(2,1))-DSig(0)*D(2,0))/D(0,0); 00439 } 00440 00441 // increments of internal values 00442 if (Mdl->NIvs>0) 00443 { 00444 Vec_t dsig_tmp; 00445 Mdl->TgIncs (_RK_state, DEps, dsig_tmp, DIvs); 00446 for (size_t i=0; i<Mdl->NIvs; ++i) dYdt[3+i] = DIvs(i); 00447 if (CheckModelTgIncs) 00448 { 00449 Vec_t err(DSig - dsig_tmp); 00450 if (Norm(err)>1.0e-8) 00451 { 00452 std::ostringstream oss; 00453 oss << " dsig_tmp = " << PrintVector(dsig_tmp); 00454 oss << " DSig = " << PrintVector(DSig); 00455 oss << " Norm(err) = " << Norm(err) << std::endl; 00456 throw new Fatal("Driver::_RK_3Comps: __internal_error__: DSig differs from dsig_tmp calculated by model\n%s",oss.str().c_str()); 00457 } 00458 } 00459 } 00460 00461 return GSL_SUCCESS; 00462 } 00463 00464 #endif