![]() |
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, Raul Durand * 00004 * Copyright (C) 2009 Sergio Galindo * 00005 * * 00006 * This program is free software: you can redistribute it and/or modify * 00007 * it under the terms of the GNU General Public License as published by * 00008 * the Free Software Foundation, either version 3 of the License, or * 00009 * any later version. * 00010 * * 00011 * This program is distributed in the hope that it will be useful, * 00012 * but WITHOUT ANY WARRANTY; without even the implied warranty of * 00013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * 00014 * GNU General Public License for more details. * 00015 * * 00016 * You should have received a copy of the GNU General Public License * 00017 * along with this program. If not, see <http://www.gnu.org/licenses/> * 00018 ************************************************************************/ 00019 00020 #ifndef MECHSYS_CAMCLAY_H 00021 #define MECHSYS_CAMCLAY_H 00022 00023 // MechSys 00024 #include <mechsys/models/elastoplastic.h> 00025 00026 class CamClay : public ElastoPlastic 00027 { 00028 public: 00029 // Constructor 00030 CamClay (int NDim, SDPair const & Prms); 00031 00032 // Derived methods 00033 void InitIvs (SDPair const & Ini, State * Sta) const; 00034 void Gradients (Vec_t const & Sig, Vec_t const & Ivs, bool Potential=false) const; 00035 void Hardening (Vec_t const & Sig, Vec_t const & Ivs) const; 00036 double YieldFunc (Vec_t const & Sig, Vec_t const & Ivs) const; 00037 double CalcE (Vec_t const & Sig, Vec_t const & Ivs) const 00038 { return fabs(Sig(0)+Sig(1)+Sig(2))*(1.0-2.0*nu)*v0/kap; } 00039 /* 00040 { 00041 double pcam = fabs(Sig(0)+Sig(1)+Sig(2))/3.0; 00042 double K = pcam*v0/kap; 00043 return Calc_E_ (K, nu); 00044 } 00045 */ 00046 00047 // Data 00048 double lam; 00049 double kap; 00050 double phi; 00051 mutable double v0; 00052 mutable double chi; 00053 mutable double Mcs; 00054 mutable double wcs; 00055 00056 // Internal methods 00057 double Calc_M (double sin3th) const { return Mcs*pow(2.0*wcs/(1.0+wcs-(1.0-wcs)*sin3th),1.0/4.0); } 00058 }; 00059 00060 00062 00063 00064 inline CamClay::CamClay (int NDim, SDPair const & Prms) 00065 : ElastoPlastic (NDim, Prms, /*niv*/4, "CamClay", /*derived*/true) 00066 { 00067 // parameters 00068 lam = Prms("lam"); 00069 kap = Prms("kap"); 00070 nu = Prms("nu"); 00071 phi = Prms("phi"); 00072 Mcs = Phi2M(phi,"oct"); 00073 double phi_rad = phi*Util::PI/180.0; 00074 wcs = pow((3.0-sin(phi_rad))/(3.0+sin(phi_rad)),4.0); 00075 00076 // internal values 00077 IvNames = "z0", "z1", "evp", "edp"; 00078 } 00079 00080 inline void CamClay::InitIvs (SDPair const & Ini, State * Sta) const 00081 { 00082 // initialize state 00083 EquilibState * sta = static_cast<EquilibState*>(Sta); 00084 sta->Init (Ini, NIvs); 00085 00086 // specific void 00087 v0 = Ini("v0"); 00088 chi = (kap-lam)/v0; 00089 00090 // internal variables 00091 Calc_pqt (sta->Sig); 00092 double M = Calc_M (t); 00093 double p0 = p+(q*q)/(p*M*M); 00094 double OCR = (Ini.HasKey("OCR") ? Ini("OCR") : 1.0); 00095 if (NewSU) 00096 { 00097 sta->Ivs(0) = p0; 00098 sta->Ivs(1) = OCR*p0; 00099 } 00100 else sta->Ivs(0) = OCR*p0; 00101 00102 // check initial yield function 00103 double f = YieldFunc (sta->Sig, sta->Ivs); 00104 if (f>FTol) throw new Fatal("CamClay:InitIvs: stress point (sig=(%g,%g,%g,%g]) is outside yield surface (f=%g) with z0=%g",sta->Sig(0),sta->Sig(1),sta->Sig(2),sta->Sig(3)/Util::SQ2,f,sta->Ivs(0)); 00105 if (NewSU && f<-FTol) throw new Fatal("CamClay:InitIvs: stress point (sig=(%g,%g,%g,%g]) is outside yield surface (f=%g) with z0=%g",sta->Sig(0),sta->Sig(1),sta->Sig(2),sta->Sig(3)/Util::SQ2,f,sta->Ivs(0)); 00106 } 00107 00108 inline void CamClay::Gradients (Vec_t const & Sig, Vec_t const & Ivs, bool Potential) const 00109 { 00110 OctInvs (Sig, p,q,t,th,s, qTol, &dthdsig); 00111 double M = Calc_M (t); 00112 Vec_t * VorW = &V; 00113 if (Potential) VorW = &W; 00114 else 00115 { 00116 Y(0) = -M*M*p; 00117 Y(1) = 0.0; 00118 Y(2) = 0.0; 00119 Y(3) = 0.0; 00120 } 00121 double dfdp = M*M*(2.0*p-Ivs(0)); 00122 double m = -dfdp/Util::SQ3; 00123 if (q>qTol) 00124 { 00125 double dMdt = 0.25*M*(1.0-wcs)/(1.0+wcs-(1.0-wcs)*t); 00126 double dtdth = 3.0*cos(3.0*th); 00127 double dMdth = dMdt*dtdth; 00128 double dfdth = -2.0*M*dMdth*(Ivs(0)-p); 00129 (*VorW) = 2.0*s + m*I + dfdth*dthdsig; 00130 } 00131 else (*VorW) = m*I; 00132 } 00133 00134 inline void CamClay::Hardening (Vec_t const & Sig, Vec_t const & Ivs) const 00135 { 00136 H(0) = Ivs(0)*Tra(W)/chi; 00137 H(1) = 0.0; 00138 H(2) = 0.0; 00139 H(3) = 0.0; 00140 if (NewSU) 00141 { 00142 double D = 2.0*Ivs(1)/(Ivs(1)+Ivs(0))-1.0; 00143 if (D<0.0) D = 0.0; 00144 H(1) = exp(-BetSU*D)*H(0); // (D>0.0 ? 0.0 : H(0)); 00145 H(0) = H(0) + AlpSU*(1.0-exp(-BetSU*D)); 00146 } 00147 } 00148 00149 inline double CamClay::YieldFunc (Vec_t const & Sig, Vec_t const & Ivs) const 00150 { 00151 Calc_pqt (Sig); 00152 double M = Calc_M (t); 00153 return q*q + (p-Ivs(0))*p*M*M; 00154 } 00155 00156 00158 00159 00160 Model * CamClayMaker(int NDim, SDPair const & Prms, Model const * O) { return new CamClay(NDim,Prms); } 00161 00162 int CamClayRegister() 00163 { 00164 ModelFactory ["CamClay"] = CamClayMaker; 00165 MODEL.Set ("CamClay", (double)MODEL.Keys.Size()); 00166 MODEL_PRM_NAMES["CamClay"].Resize(7); 00167 MODEL_PRM_NAMES["CamClay"] = "lam", "kap", "nu", "phi", "newsu", "betsu", "alpsu"; 00168 MODEL_IVS_NAMES["CamClay"].Resize(2); 00169 MODEL_IVS_NAMES["CamClay"] = "v0", "OCR"; 00170 return 0; 00171 } 00172 00173 int __CamClay_dummy_int = CamClayRegister(); 00174 00175 #endif // MECHSYS_CAMCLAY_H