82#ifdef SOPHISTICATED_SIZEDEPENDENT_ADJUSTMENT
107 fprintf(file,
"\tstatus { ");
112 fprintf(file,
"statusflag 0 (Elastic),");
115 fprintf(file,
"statusflag 1 (Unloading),");
118 fprintf(file,
"statusflag 2 (Plastic),");
121 fprintf(file,
"statusflag 3 (Damage),");
124 fprintf(file,
"statusflag 4 (PlasticDamage),");
127 fprintf(file,
"statusflag 5 (VertexCompression),");
130 fprintf(file,
"statusflag 6 (VertexTension),");
133 fprintf(file,
"statusflag 7 (VertexCompressionDamage),");
136 fprintf(file,
"statusflag 8 (VertexTensionDamage),");
143 giveFullPlasticStrainVector(plasticStrainVector);
144 fprintf(file,
"plastic strains ");
145 for (
auto &val : plasticStrainVector ) {
146 fprintf(file,
" %.4e", val);
155 fprintf(file,
", damage %.4e",
damage);
158 fprintf(file,
"}\n");
210 #ifdef SOPHISTICATED_SIZEDEPENDENT_ADJUSTMENT
268 #ifdef SOPHISTICATED_SIZEDEPENDENT_ADJUSTMENT
279 if ( type == IST_DamageScalar ) {
284 if ( type == IST_CumPlasticStrain ) {
289 if ( type == IST_CumPlasticStrain_2 ) {
327 gM =
eM / ( 2. * ( 1. +
nu ) );
328 kM =
eM / ( 3. * ( 1. - 2. *
nu ) );
364#ifdef SOPHISTICATED_SIZEDEPENDENT_ADJUSTMENT
370 m = 3. * ( pow(
fc, 2.) - pow(
ft, 2.) ) / (
fc *
ft ) *
ecc / (
ecc + 1. );
388 status->initTempStatus();
394 auto strain = totalStrain - thermalStrain;
402 auto tempDamage = tempDamKapD.first;
403 auto tempKappaD = tempDamKapD.second;
406 const auto &tempPlasticStrain = status->giveTempPlasticStrain();
407 auto elasticStrain = strain - tempPlasticStrain;
411 auto stress = effectiveStress * ( 1. - tempDamage );
413 status->letTempKappaDBe(tempKappaD);
414 status->letTempDamageBe(tempDamage);
416 status->letTempStrainVectorBe(totalStrain);
417 status->letTempStressVectorBe(stress);
423#ifdef SOPHISTICATED_SIZEDEPENDENT_ADJUSTMENT
426 if ( status->giveEpsLoc() < 0. ) {
427 FloatArray strainIncrement = totalStrain - status->giveStrainVector();
428 auto stressIncrement = stress -
FloatArrayF< 6 >(status->giveStressVector() );
430 double work = strainIncrement.
dotProduct(stressIncrement, n);
433 double E = this->
give(
'E', gp);
435 double tmpEpsloc = tempKappaD + tempDamage *
ft /
E;
436 status->letTempEpslocBe(tmpEpsloc);
445std::pair< double, double >
450 double f = equivStrain - status->giveKappaD();
453 double tempKappaD = status->giveKappaD();
454 double tempDamage = status->giveDamage();
456 tempDamage, tempKappaD
460 double tempKappaD = equivStrain;
461#ifdef SOPHISTICATED_SIZEDEPENDENT_ADJUSTMENT
462 if ( (
href <= 0. ) || ( status->giveEpsLoc() >= 0. ) ) {
472 tempDamage, tempKappaD
482 auto tempKappaP = status->giveTempKappaP();
483 auto kappaP = status->giveKappaP();
484 double equivStrain = status->giveEquivStrain();
485 double deltaEquivStrain = 0.;
486 double tempEquivStrain = 0.;
487 if ( tempKappaP <= 1.0 || tempKappaP == kappaP ) {
489 }
else if ( tempKappaP > 1.0 && tempKappaP != kappaP ) {
490 const auto &plasticStrain = status->givePlasticStrain();
491 const auto &tempPlasticStrain = status->giveTempPlasticStrain();
493 double volumetricPlasticStrain = plasticStrain [ 0 ] + plasticStrain [ 1 ] + plasticStrain [ 2 ];
494 double tempVolumetricPlasticStrain = tempPlasticStrain [ 0 ] + tempPlasticStrain [ 1 ] + tempPlasticStrain [ 2 ];
495 if ( kappaP < 1.0 ) {
497 double peakVolumetricPlasticStrain = ( 1. - kappaP ) / ( tempKappaP - kappaP ) *
498 ( tempVolumetricPlasticStrain - volumetricPlasticStrain ) +
499 volumetricPlasticStrain;
500 if ( peakVolumetricPlasticStrain < 0. ) {
501 peakVolumetricPlasticStrain = 0.;
504 deltaEquivStrain = tempVolumetricPlasticStrain - peakVolumetricPlasticStrain;
506 if ( tempEquivStrain < 0. ) {
507 tempEquivStrain = 0.;
510 deltaEquivStrain = ( tempVolumetricPlasticStrain - volumetricPlasticStrain );
511 if ( deltaEquivStrain < 0. ) {
512 deltaEquivStrain = 0.;
515 tempEquivStrain = equivStrain +
520 status->letTempEquivStrainBe(tempEquivStrain);
521 status->letDeltaEquivStrainBe(deltaEquivStrain);
522 return tempEquivStrain;
529 double le = status->giveLe();
540 double answer = -( this->
ef / le ) * log(1. - dam) - dam *
ft /
eM;
544#define DPM_DAMAGE_TOLERANCE 1.e-8
555 double R, Lhs, aux, aux1;
557 double h = status->
giveLe();
559#ifdef SOPHISTICATED_SIZEDEPENDENT_ADJUSTMENT
562 if ( (
href <= 0. ) || ( epsloc < 0. ) ) {
569 aux1 = (
ft /
eM ) * h /
ef;
571 printf(
"computeDamageParam: ft=%g, E=%g, wf=%g, hmax=E*wf/ft=%g, h=%g\n",
ft,
eM,
ef,
eM *
ef /
ft, h);
577 aux = exp(-h * ( omega *
ft /
eM + kappa ) /
ef);
578 R = 1. - omega - aux;
579 Lhs = -1. + aux1 * aux;
586#ifdef SOPHISTICATED_SIZEDEPENDENT_ADJUSTMENT
594 aux1 = (
ft /
eM ) * h /
ef;
597 aux = exp(-( (
href - h ) * epsloc + h * ( omega *
ft /
eM + kappa ) ) /
ef);
598 R = 1. - omega - aux;
599 Lhs = -1. + aux1 * aux;
602 printf(
"computeDamageParam: algorithm not converging (part 2)");
608 if ( ( omega > 1.0 ) || ( omega < 0.0 ) ) {
624 if ( kappaD <= 0. ) {
629 status->setLe(
helem);
630 }
else if ( status->giveDamage() == 0. ) {
633 auto principalStrains = tmp.first;
634 auto principalDir = tmp.second;
637 for (
int i = 2; i <= 3; i++ ) {
638 if ( principalStrains.at(i) > principalStrains.at(indx) ) {
644 for (
int i = 1; i <= 3; i++ ) {
645 crackPlaneNormal.
at(i) = principalDir.at(i, indx);
656 }
else if ( status->giveLe() == 0. ) {
668 const auto &plasticStrain = status->givePlasticStrain();
669 auto tempPlasticStrain = status->giveTempPlasticStrain() - plasticStrain;
671 double volStrain = tempPlasticStrain [ 0 ] + tempPlasticStrain [ 1 ] + tempPlasticStrain [ 2 ];
675 double negativeVolStrain = 0.;
676 for (
int i = 0; i < 3; i++ ) {
677 if ( principalStrain [ i ] < 0. ) {
678 negativeVolStrain += principalStrain [ i ];
683 double Rs = -negativeVolStrain / volStrain;
685 return 1. +
ASoft * pow(Rs, 2.);
687 return 1. - 3. *
ASoft + 4. *
ASoft * sqrt(Rs);
700 auto tempPlasticStrain = status->giveTempPlasticStrain();
701 auto tempKappaP = status->giveTempKappaP();
704 auto elasticStrain = strain - tempPlasticStrain;
710 double sig = std::get< 0 >(tmp);
711 double rho = std::get< 1 >(tmp);
712 double thetaTrial = std::get< 2 >(tmp);
717 double apexStress = 0.;
726 tempKappaP = status->giveTempKappaP();
740 tempPlasticStrain = strain - elasticStrain;
741 status->letTempPlasticStrainBe(tempPlasticStrain);
748 const double tempKappa,
754 double apexCompression = 0.;
757 if ( ( tempKappa < 1. ) && ( sig < 0. ) ) {
759 double sigZero = -15. *
fc;
764 FZero = pow( ( 1. - yieldHardOne ), 2. ) * pow( ( sigZero /
fc ), 4. ) +
765 pow(yieldHardOne, 2.) *
m * ( sigZero /
fc ) - pow(yieldHardOne, 2.);
767 double dFZeroDSigZero = pow( ( 1. - yieldHardOne ), 2. ) * 4. * pow( ( sigZero /
fc ), 3. ) /
fc +
768 pow(yieldHardOne, 2.) *
m /
fc;
770 sigZero = sigZero - FZero / dFZeroDSigZero;
773 if ( l < 15 && sigZero < 0. ) {
774 apexCompression = sigZero;
776 apexCompression = -15. *
fc;
780 if ( ( sig > 0. && tempKappa < 1. ) || ( sig >
fc /
m && tempKappa >= 1. ) ) {
783 }
else if ( sig < apexCompression ) {
784 answer = apexCompression;
799 auto stressPrincipalDir = tmp.second;
804 auto deviatoricStress = tmp2.first;
805 double sig = tmp2.second;
807 double deltaLambda = 0.;
809 const double volumetricPlasticStrain = 3. * status->giveVolumetricPlasticStrain();
811 const double deviatoricPlasticStrainNorm = status->giveDeviatoricPlasticStrainNorm();
813 double tempVolumetricPlasticStrain = volumetricPlasticStrain;
814 double tempDeviatoricPlasticStrainNorm = deviatoricPlasticStrainNorm;
816 const double kappaP = status->giveKappaP();
817 auto tempKappaP = kappaP;
820 double residualNorm = fabs(yieldValue);
822 int negativeRhoFlag = 0;
824 int iterationCount = 0;
827 OOFEM_ERROR(
"Closest point projection did not converge.");
838 residual [ 0 ] = volumetricPlasticStrain - tempVolumetricPlasticStrain +
839 deltaLambda * dGDInv [ 0 ];
840 residual [ 1 ] = deviatoricPlasticStrainNorm -
841 tempDeviatoricPlasticStrainNorm + deltaLambda * dGDInv [ 1 ];
842 residual [ 2 ] = kappaP - tempKappaP + deltaLambda * dKappaDDeltaLambda;
847 residualNorm = pow(residual [ 0 ], 2.) + pow(residual [ 1 ], 2.) +
848 pow(residual [ 2 ], 2.) + pow(yieldValue, 2.);
849 residualNorm = sqrt(residualNorm);
853 auto aMatrix =
computeAMatrix(sig, rho, theta, tempKappaP, deltaLambda);
857 for (
int i = 0; i < 2; i++ ) {
858 derivativesOfYieldSurface [ i ] = dFDInv [ i ];
861 derivativesOfYieldSurface [ 2 ] = dFDKappa;
864 for (
int i = 0; i < 2; i++ ) {
865 flowRules [ i ] = dGDInv [ i ];
868 flowRules [ 2 ] = dKappaDDeltaLambda;
871 double deltaLambdaIncrement = yieldValue;
872 auto helpVectorA =
dot(aMatrix, residual);
873 for (
int i = 0; i < 3; i++ ) {
874 deltaLambdaIncrement -= derivativesOfYieldSurface [ i ] * helpVectorA [ i ];
877 auto helpVectorB =
dot(aMatrix, flowRules);
878 double denominator = 0.;
879 for (
int i = 0; i < 3; i++ ) {
880 denominator += derivativesOfYieldSurface [ i ] * helpVectorB [ i ];
883 deltaLambdaIncrement /= denominator;
886 auto answerIncrement = -
dot(aMatrix, ( residual + deltaLambdaIncrement * flowRules ) );
887 auto rhoTest = rho + answerIncrement [ 1 ];
890 double tempKappaPTest = 0.;
891 if ( rhoTest < 0. && negativeRhoFlag == 0 ) {
893 answerIncrement [ 1 ] = -rho;
895 double deltaLambdaIncrementNew =
896 ( -aMatrix(1, 0) * residual [ 0 ] - aMatrix(1, 1) * residual [ 1 ] -
897 aMatrix(1, 2) * residual [ 2 ] - answerIncrement [ 1 ] ) /
898 ( flowRules [ 0 ] * aMatrix(1, 0) + flowRules [ 1 ] * aMatrix(1, 1) +
899 flowRules [ 2 ] * aMatrix(1, 2) );
902 if ( fabs(deltaLambdaIncrementNew) <
yieldTol * 1.e3 ) {
904 deltaLambdaIncrementNew = deltaLambdaIncrement;
907 answerIncrement = -
dot(aMatrix, ( residual + deltaLambdaIncrementNew * flowRules ) );
909 sig += answerIncrement [ 0 ];
910 rho += answerIncrement [ 1 ];
912 tempKappaPTest = tempKappaP;
913 tempKappaP += answerIncrement [ 2 ];
914 deltaLambda += deltaLambdaIncrementNew;
916 tempKappaPTest = tempKappaP;
917 tempKappaP += answerIncrement [ 2 ];
918 sig += answerIncrement [ 0 ];
919 rho += answerIncrement [ 1 ];
921 deltaLambda += deltaLambdaIncrement;
925 if ( ( tempKappaP - status->giveKappaP() ) < 0. ) {
926 tempKappaP = tempKappaPTest;
929 tempVolumetricPlasticStrain -= answerIncrement [ 0 ] / (
kM );
930 tempDeviatoricPlasticStrainNorm -= answerIncrement [ 1 ] / ( 2. *
gM );
938 status->letTempVolumetricPlasticStrainBe(tempVolumetricPlasticStrain / 3.);
939 if ( deltaLambda < 0 ) {
940 printf(
"deltaLambda = %e\n", deltaLambda);
941 printf(
"plastic multiplier less than zero");
945 status->letDeltaLambdaBe(deltaLambda);
947 stressPrincipal [ 0 ] = sig + sqrt(2. / 3.) * rho * cos(theta);
948 stressPrincipal [ 1 ] = sig + sqrt(2. / 3.) * rho * cos(theta - 2. *
M_PI / 3.);
949 stressPrincipal [ 2 ] = sig + sqrt(2. / 3.) * rho * cos(theta + 2. *
M_PI / 3.);
954 status->letTempKappaPBe(tempKappaP);
967 auto deviatoricStressTrial = tmp.first;
968 auto sigTrial = tmp.second;
972 double tempKappaP = status->giveTempKappaP();
973 const double kappaInitial = tempKappaP;
989 if ( yieldValue * yieldValueMid >= 0. ) {
995 double ratioPotential;
998 if ( yieldValue < 0.0 ) {
999 dSig = sig2 - sigTrial;
1002 dSig = sigTrial - sig2;
1006 for (
int j = 0; j < 250; j++ ) {
1009 double sigMid = sigAnswer + dSig;
1016 if ( yieldValueMid <= 0. ) {
1020 if ( fabs(yieldValueMid) <
yieldTol && yieldValueMid <= 0. ) {
1021 for (
int i = 0; i < 3; i++ ) {
1022 effectiveStress [ i ] = sigAnswer;
1025 for (
int i = 3; i < effectiveStress.
giveSize(); i++ ) {
1026 effectiveStress [ i ] = 0.;
1031 double ratioTrial = rhoTrial / ( sigTrial - sigAnswer );
1046 status->letTempKappaPBe(tempKappaP);
1052 const double sigTrial,
1053 const double rhoTrial,
1054 const double sig)
const
1057 double equivalentDeltaPlasticStrain = sqrt(1. / 9. * pow( ( sigTrial - sig ) / (
kM ), 2. ) + pow(rhoTrial / ( 2. *
gM ), 2.) );
1060 double thetaVertex = 0.;
1063 return kappaInitial + equivalentDeltaPlasticStrain / ductilityMeasure;
1071 const double tempKappa)
const
1078 const double rFunction = ( 4. * ( 1. - pow(
ecc, 2.) ) * pow(cos(theta), 2.) +
1079 pow( ( 2. *
ecc - 1. ), 2. ) ) /
1080 ( 2. * ( 1. - pow(
ecc, 2.) ) * cos(theta) +
1081 ( 2. *
ecc - 1. ) * sqrt(4. * ( 1. - pow(
ecc, 2.) ) * pow(cos(theta), 2.)
1082 + 5. * pow(
ecc, 2.) - 4. *
ecc) );
1085 const double Al = ( 1. - yieldHardOne ) * pow( ( sig /
fc + rho / ( sqrt(6.) *
fc ) ), 2. ) +
1086 sqrt(3. / 2.) * rho /
fc;
1089 return pow(Al, 2.) +
1090 pow(yieldHardOne, 2.) *
m * ( sig /
fc + rho * rFunction / ( sqrt(6.) *
fc ) ) -
1091 pow(yieldHardTwo, 2.);
1099 const double tempKappa)
const
1110 const double rFunction =
1111 ( 4. * ( 1. -
ecc *
ecc ) * cos(theta) * cos(theta) + ( 2. *
ecc - 1. ) * ( 2. *
ecc - 1. ) ) /
1112 ( 2 * ( 1. -
ecc *
ecc ) * cos(theta) + ( 2. *
ecc - 1. ) *
1113 sqrt(4. * ( 1. -
ecc *
ecc ) * cos(theta) * cos(theta) + 5. *
ecc *
ecc - 4. *
ecc) );
1116 const double Al = ( 1. - yieldHardOne ) * pow( ( sig /
fc + rho / ( sqrt(6.) *
fc ) ), 2. ) + sqrt(3. / 2.) * rho /
fc;
1118 const double Bl = sig /
fc + rho / (
fc * sqrt(6.) );
1120 const double dFDYieldHardOne = -2. * Al * pow(Bl, 2.)
1121 + 2. * yieldHardOne *
m * ( sig /
fc + rho * rFunction / ( sqrt(6.) *
fc ) );
1123 const double dFDYieldHardTwo = -2. * yieldHardTwo;
1126 double dFDKappa = dFDYieldHardOne * dYieldHardOneDKappa +
1127 dFDYieldHardTwo * dYieldHardTwoDKappa;
1135 if ( dFDKappa > 0. ) {
1146 const double tempKappa)
const
1154 const double rFunction = ( 4. * ( 1. -
ecc *
ecc ) * cos(theta) * cos(theta) + ( 2. *
ecc - 1. ) * ( 2. *
ecc - 1. ) ) /
1155 ( 2. * ( 1. -
ecc *
ecc ) * cos(theta) + ( 2. *
ecc - 1. ) * sqrt(4. * ( 1. -
ecc *
ecc ) * cos(theta) * cos(theta)
1159 const double AL = ( 1. - yieldHardOne ) * pow( ( sig /
fc + rho / ( sqrt(6.) *
fc ) ), 2. ) + sqrt(3. / 2.) * rho /
fc;
1160 const double BL = sig /
fc + rho / (
fc * sqrt(6.) );
1163 const double dfdsig = 4. * ( 1. - yieldHardOne ) /
fc *
AL * BL + yieldHardOne * yieldHardOne *
m /
fc;
1165 const double dfdrho =
AL / ( sqrt(6.) *
fc ) * ( 4. * ( 1. - yieldHardOne ) * BL + 6. ) + rFunction *
m * yieldHardOne * yieldHardOne / ( sqrt(6.) *
fc );
1176 const double tempKappa)
const
1181 double equivalentDGDStress = sqrt(1. / 3. * pow(dGDInv [ 0 ], 2.) +
1182 pow(dGDInv [ 1 ], 2.) );
1185 double dKappaDDeltaLambda = equivalentDGDStress / ductilityMeasure;
1186 return dKappaDDeltaLambda;
1194 const double tempKappa)
const
1201 double equivalentDGDStress = sqrt(1. / 3. * pow(dGDInv [ 0 ], 2.) +
1202 pow(dGDInv [ 1 ], 2.) );
1209 dEquivalentDGDStressDInv [ 0 ] =
1210 ( 2. / 3. * dGDInv [ 0 ] * dDGDDInv(0, 0) + 2. * dGDInv [ 1 ] * dDGDDInv(1, 0) ) / ( 2. * equivalentDGDStress );
1211 dEquivalentDGDStressDInv [ 1 ] =
1212 ( 2. / 3. * dGDInv [ 0 ] * dDGDDInv(0, 1) + 2. * dGDInv [ 1 ] * dDGDDInv(1, 1) ) / ( 2. * equivalentDGDStress );
1218 answer [ 0 ] = ( dEquivalentDGDStressDInv [ 0 ] * ductilityMeasure - equivalentDGDStress * dDuctilityMeasureDInv [ 0 ] ) / pow(ductilityMeasure, 2.);
1219 answer [ 1 ] = ( dEquivalentDGDStressDInv [ 1 ] * ductilityMeasure - equivalentDGDStress * dDuctilityMeasureDInv [ 1 ] ) / pow(ductilityMeasure, 2.);
1227 const double tempKappa)
const
1233 double equivalentDGDStress = sqrt(1. / 3. * pow(dGDInv [ 0 ], 2.) + pow(dGDInv [ 1 ], 2.) );
1239 double dEquivalentDGDStressDKappa =
1240 ( 2. / 3. * dGDInv [ 0 ] * dDGDInvDKappa [ 0 ] + 2. * dGDInv [ 1 ] * dDGDInvDKappa [ 1 ] ) / ( 2. * equivalentDGDStress );
1243 double dDuctilityMeasureDKappa = 0.;
1245 double dDKappaDDeltaLambdaDKappa =
1246 ( dEquivalentDGDStressDKappa * ductilityMeasure -
1247 equivalentDGDStress * dDuctilityMeasureDKappa ) / pow(ductilityMeasure, 2.);
1249 return dDKappaDDeltaLambdaDKappa;
1255 const double theta)
const
1257 double thetaConst = pow(2. * cos(theta), 2.);
1258 double ductilityMeasure;
1259 double x = -( sig +
fc / 3 ) /
fc;
1263 double fZero =
BHard;
1265 double CHelp =
DHard;
1266 double AHelp = fZero - CHelp;
1267 double BHelp = ( fZero - CHelp ) / fPrimeZero;
1268 ductilityMeasure = ( AHelp * exp(x / BHelp) + CHelp ) / thetaConst;
1273 if ( ductilityMeasure <= 0. ) {
1274 printf(
"ductilityMeasure is zero or negative");
1277 return ductilityMeasure;
1284 const double tempKappa)
const
1286 double thetaConst = pow(2. * cos(theta), 2.);
1287 double x = ( -( sig +
fc / 3 ) ) /
fc;
1289 double dXDSig = -1. /
fc;
1292 double fZero =
BHard;
1294 double CHelp =
DHard;
1295 double AHelp = fZero - CHelp;
1296 double BHelp = ( fZero - CHelp ) / fPrimeZero;
1297 double dDuctilityMeasureDX = AHelp / BHelp * exp(x / BHelp) / thetaConst;
1299 dDuctilityMeasureDX *dXDSig, 0.
1302 double dXDSig = -1. /
fc;
1303 double dDuctilityMeasureDX = -(
BHard -
AHard ) / (
CHard ) / thetaConst * exp(-x / (
CHard ) );
1305 dDuctilityMeasureDX *dXDSig, 0.
1314 const double tempKappa)
const
1317 const double R = ( sig -
ft / 3. ) /
fc;
1318 const double mQTension = ( 3. *
ft /
fc +
m / 2. );
1319 const double mQCompression =
1321 const double AConst = -(
ft +
fc ) / ( 3. *
fc ) / log(mQCompression / mQTension);
1322 const double mQ = mQTension * exp(R / AConst);
1327 const double Bl = sig /
fc + rho / (
fc * sqrt(6.) );
1329 const double Al = ( 1. - yieldHardOne ) * pow(Bl, 2.) + sqrt(3. / 2.) * rho /
fc;
1331 const double dgdsig = 4. * ( 1. - yieldHardOne ) /
fc * Al * Bl + yieldHardOne * yieldHardOne *
mQ /
fc;
1333 const double dgdrho = Al / ( sqrt(6.) *
fc ) * ( 4. * ( 1. - yieldHardOne ) * Bl + 6. ) +
1334 m * pow(yieldHardOne, 2.) / ( sqrt(6.) *
fc );
1344 const double tempKappa)
const
1347 const double R = ( sig -
ft / 3. ) /
fc;
1348 const double mQTension = ( 3. *
ft /
fc +
m / 2. );
1349 const double mQCompression =
1351 const double AConst = -(
ft +
fc ) / ( 3. *
fc ) / log(mQCompression / mQTension);
1352 const double mQ = mQTension * exp(R / AConst);
1357 const double Bl = sig /
fc;
1359 const double Al = ( 1. - yieldHardOne ) * pow(Bl, 2.);
1361 const double dgdsig = 4. * ( 1. - yieldHardOne ) /
fc * Al * Bl + yieldHardOne * yieldHardOne *
mQ /
fc;
1363 const double dgdrho = Al / ( sqrt(6.) *
fc ) * ( 4. * ( 1. - yieldHardOne ) * Bl + 6. ) +
1364 m * pow(yieldHardOne, 2.) / ( sqrt(6.) *
fc );
1368 return dgdrho / dgdsig * 3. * ( 1. - 2. *
nu ) / ( 1. +
nu );
1375 const double tempKappa)
const
1378 const double R = ( sig -
ft / 3. ) /
fc;
1379 const double mQTension = ( 3. *
ft /
fc +
m / 2. );
1380 const double mQCompression =
1382 const double AConst = -(
ft +
fc ) / ( 3. *
fc ) / log(mQCompression / mQTension);
1383 const double mQ = mQTension * exp(R / AConst);
1389 const double Bl = sig /
fc + rho / (
fc * sqrt(6.) );
1391 const double Al = ( 1. - yieldHardOne ) * pow(Bl, 2.) + sqrt(3. / 2.) * rho /
fc;
1393 const double dAlDYieldHard = -pow(Bl, 2.);
1395 const double dDGDSigDKappa =
1396 ( -4. * Al * Bl /
fc + 4. * ( 1 - yieldHardOne ) /
fc * dAlDYieldHard * Bl +
1397 2. * yieldHardOne *
mQ /
fc ) * dYieldHardOneDKappa;
1399 const double dDGDRhoDKappa =
1400 ( dAlDYieldHard / ( sqrt(6.) *
fc ) * ( 4. * ( 1. - yieldHardOne ) * Bl + 6. ) -
1401 4. * Al / ( sqrt(6.) *
fc ) * Bl + 2. *
m * yieldHardOne / ( sqrt(6.) *
fc ) ) * dYieldHardOneDKappa;
1404 dDGDSigDKappa, dDGDRhoDKappa
1411 const double tempKappa)
const
1414 const double R = ( sig -
ft / 3. ) /
fc;
1415 const double mQTension = ( 3. *
ft /
fc +
m / 2. );
1416 const double mQCompression =
1418 const double AConst = -(
ft +
fc ) / ( 3. *
fc ) / log(mQCompression / mQTension);
1420 const double dMQDSig = mQTension / ( AConst *
fc ) * exp(R / AConst);
1426 const double Bl = sig /
fc + rho / (
fc * sqrt(6.) );
1428 const double Al = ( 1. - yieldHardOne ) * pow(Bl, 2.) +
1429 sqrt(3. / 2.) * rho /
fc;
1431 const double dAlDSig = 2. * ( 1. - yieldHardOne ) * Bl /
fc;
1432 const double dBlDSig = 1. /
fc;
1434 const double dAlDRho = 2. * ( 1. - yieldHardOne ) * Bl / (
fc * sqrt(6.) ) + sqrt(3. / 2.) /
fc;
1435 const double dBlDRho = 1. / (
fc * sqrt(6.) );
1438 const double ddgddSig = 4. * ( 1. - yieldHardOne ) /
fc * ( dAlDSig * Bl + Al * dBlDSig ) +
1439 yieldHardOne * yieldHardOne * dMQDSig /
fc;
1441 const double ddgddRho = dAlDRho / ( sqrt(6.) *
fc ) * ( 4. * ( 1. - yieldHardOne ) * Bl + 6. ) +
1442 Al * dBlDRho * 4. * ( 1. - yieldHardOne ) / ( sqrt(6.) *
fc );
1444 const double ddgdSigdRho = 4. * ( 1. - yieldHardOne ) /
fc * ( dAlDRho * Bl + Al * dBlDRho );
1446 const double ddgdRhodSig = dAlDSig / ( sqrt(6.) *
fc ) * ( 4. * ( 1. - yieldHardOne ) * Bl + 6. )
1447 + Al / ( sqrt(6.) *
fc ) * ( 4. * ( 1. - yieldHardOne ) * dBlDSig );
1450 answer(0, 0) = ddgddSig;
1451 answer(0, 1) = ddgdSigdRho;
1452 answer(1, 0) = ddgdRhodSig;
1453 answer(1, 1) = ddgddRho;
1461 const double tempKappa,
1462 const double deltaLambda)
const
1470 aMatrixInverse(0, 0) = 1. / (
kM ) + deltaLambda * dDGDDInv(0, 0);
1471 aMatrixInverse(0, 1) = deltaLambda * dDGDDInv(0, 1);
1472 aMatrixInverse(0, 2) = deltaLambda * dDGDInvDKappa [ 0 ];
1474 aMatrixInverse(1, 0) = deltaLambda * dDGDDInv(1, 0);
1475 aMatrixInverse(1, 1) = 1. / ( 2. *
gM ) + deltaLambda * dDGDDInv(1, 1);
1476 aMatrixInverse(1, 2) = deltaLambda * dDGDInvDKappa [ 1 ];
1478 aMatrixInverse(2, 0) = deltaLambda * dDKappaDDeltaLambdaDInv [ 0 ];
1479 aMatrixInverse(2, 1) = deltaLambda * dDKappaDDeltaLambdaDInv [ 1 ];
1480 aMatrixInverse(2, 2) = -1. + deltaLambda * dDKappaDDeltaLambdaDKappa;
1482 return inv(aMatrixInverse);
1490 if ( kappa <= 0. ) {
1492 }
else if ( kappa > 0. && kappa < 1. ) {
1494 kappa * ( pow(kappa, 2.) - 3. * kappa + 3. );
1506 }
else if ( kappa >= 0. && kappa < 1. ) {
1507 return ( 1. -
yieldHardInitial ) * ( 3. * pow(kappa, 2.) - 6. * kappa + 3. );
1520 if ( mode == SecantStiffness || mode == TangentStiffness ) {
1521 double omega = status->giveTempDamage();
1522 if ( omega > 0.9999 ) {
1526 return d * ( 1. - omega );
1533std::tuple< double, double, double >
1538 auto deviatoricStress = tmp.first;
1539 double sig = tmp.second;
1542 return std::tuple< double, double, double > {
1543 sig, rho, thetaTrial
1553 const auto &damage = status->giveDamage();
1554 const auto &tempDamage = status->giveTempDamage();
1555 const auto &kappaP = status->giveKappaP();
1556 const auto &tempKappaP = status->giveTempKappaP();
1558 if ( tempKappaP > kappaP ) {
1559 if ( tempDamage > damage ) {
1566 const int state_flag = status->giveStateFlag();
1568 if ( tempDamage > damage ) {
1576 if ( tempDamage > damage ) {
1595 auto dJ2DStress = deviatoricStress;
1596 for (
int i = 3; i < 6; i++ ) {
1597 dJ2DStress [ i ] = deviatoricStress [ i ] * 2.0;
1601 auto dRhoDStress = dJ2DStress * ( 1. / rho );
1609 for (
int i = 0; i < 3; i++ ) {
1610 answer [ i ] = 1. / 3.;
1613 for (
int i = 3; i < size; i++ ) {
1627 auto dJ2dstress = deviatoricStress;
1628 for (
int i = 3; i < 6; i++ ) {
1629 dJ2dstress [ i ] = deviatoricStress [ i ] * 2.;
1634 for (
int i = 0; i < 6; i++ ) {
1636 ddJ2ddstress(i, i) = 2. / 3.;
1640 ddJ2ddstress(i, i) = 2.;
1644 ddJ2ddstress(0, 1) = -1. / 3.;
1645 ddJ2ddstress(0, 2) = -1. / 3.;
1646 ddJ2ddstress(1, 0) = -1. / 3.;
1647 ddJ2ddstress(1, 2) = -1. / 3.;
1648 ddJ2ddstress(2, 0) = -1. / 3.;
1649 ddJ2ddstress(2, 1) = -1. / 3.;
1652 auto dJ2DJ2 =
dyad(dJ2dstress, dJ2dstress);
1655 auto ddRhoddStress = ddJ2ddstress * ( 1. / rho ) + dJ2DJ2 * ( -1. / ( rho * rho * rho ) );
1656 return ddRhoddStress;
1671 auto principalDeviatoricStress = tmp.first;
1672 auto principalDir = tmp.second;
1676 ds1DStress [ 0 ] = principalDir(0, 0) * principalDir(0, 0) - 1. / 3.;
1677 ds1DStress [ 1 ] = principalDir(1, 0) * principalDir(1, 0) - 1. / 3.;
1678 ds1DStress [ 2 ] = principalDir(2, 0) * principalDir(2, 0) - 1. / 3.;
1679 ds1DStress [ 3 ] = 2. * principalDir(1, 0) * principalDir(2, 0);
1680 ds1DStress [ 4 ] = 2. * principalDir(2, 0) * principalDir(0, 0);
1681 ds1DStress [ 5 ] = 2. * principalDir(0, 0) * principalDir(1, 0);
1684 auto dCosThetaDStress = ds1DStress * ( sqrt(3. / 2.) * rho / pow(rho, 2.) ) +
1685 computeDRhoDStress(stress) * ( -sqrt(3. / 2.) * principalDeviatoricStress [ 0 ] / pow(rho, 2.) );
1686 return dCosThetaDStress;
1692 double ACostheta = 4. * ( 1. -
ecc *
ecc ) * cos(theta) * cos(theta) +
1693 ( 2. *
ecc - 1. ) * ( 2. *
ecc - 1. );
1694 double BCostheta = 2. * ( 1. -
ecc *
ecc ) * cos(theta) +
1695 ( 2. *
ecc - 1. ) * sqrt(4. * ( 1. -
ecc *
ecc ) * cos(theta) * cos(theta)
1697 double A1Costheta = 8. * ( 1. - pow(
ecc, 2.) ) * cos(theta);
1698 double B1Costheta = 2. * ( 1. - pow(
ecc, 2.) ) +
1699 4. * ( 2. *
ecc - 1. ) * ( 1. - pow(
ecc, 2.) ) * cos(theta) /
1700 sqrt(4. * ( 1. - pow(
ecc, 2.) ) * pow(cos(theta), 2.) +
1701 5. * pow(
ecc, 2.) - 4. *
ecc);
1702 double dRDCostheta = A1Costheta / BCostheta - ACostheta / pow(BCostheta, 2.) * B1Costheta;
1714 status->letKappaDBe(kappaD);
1715 status->letEquivStrainBe(kappaD);
1717 const auto &damage = status->giveDamage();
1721 if ( damage < 1. ) {
1723 effectiveStress *= -1. / ( 1. - damage );
1725 auto plasticStrain =
solve(D, effectiveStress);
1726 status->letPlasticStrainBe(plasticStrain);
1735 if ( status->setIPValue(value, type) ) {
1749 if ( type == IST_PlasticStrainTensor ) {
1750 answer = status->givePlasticStrain();
1752 }
else if ( type == IST_DamageScalar ) {
1754 answer.
at(1) = status->giveDamage();
1756 }
else if ( type == IST_DamageTensor ) {
1759 answer.
at(1) = answer.
at(2) = answer.
at(3) = status->giveDamage();
1761 }
else if ( type == IST_PrincipalDamageTensor ) {
1764 answer.
at(1) = answer.
at(2) = answer.
at(3) = status->giveDamage();
1766 }
else if ( type == IST_DamageTensorTemp ) {
1768 answer.
at(1) = status->giveTempDamage();
1770 }
else if ( type == IST_CumPlasticStrain ) {
1772 answer.
at(1) = status->giveKappaP();
1774 }
else if ( type == IST_CumPlasticStrain_2 ) {
1776 answer.
at(1) = status->giveKappaD();
1778 }
else if ( type == IST_VolumetricPlasticStrain ) {
1780 answer.
at(1) = status->giveVolumetricPlasticStrain();
1787std::unique_ptr<MaterialStatus>
1790 return std::make_unique<ConcreteDPMStatus>(gp);
1828 if ( !stream.
write(
m) ) {
1858 #ifdef SOPHISTICATED_SIZEDEPENDENT_ADJUSTMENT
1872 if ( !stream.
read(
fc) ) {
1875 if ( !stream.
read(
ft) ) {
1902 if ( !stream.
read(
m) ) {
1905 if ( !stream.
read(
mQ) ) {
1911 if ( !stream.
read(
eM) ) {
1914 if ( !stream.
read(
gM) ) {
1917 if ( !stream.
read(
kM) ) {
1920 if ( !stream.
read(
nu) ) {
1923 if ( !stream.
read(
ef) ) {
1932 #ifdef SOPHISTICATED_SIZEDEPENDENT_ADJUSTMENT
#define REGISTER_Material_Alt(class, altname)
#define REGISTER_Material(class)
void saveContext(DataStream &stream, ContextMode mode) override
ConcreteDPMStatus(GaussPoint *gp)
Constructor.
@ ConcreteDPM_VertexCompressionDamage
@ ConcreteDPM_VertexTensionDamage
@ ConcreteDPM_PlasticDamage
@ ConcreteDPM_VertexTension
@ ConcreteDPM_VertexCompression
FloatArrayF< 6 > tempPlasticStrain
void printOutputAt(FILE *file, TimeStep *tStep) const override
Print receiver's output to given stream.
int setIPValue(const FloatArray &value, InternalStateType type)
void initTempStatus() override
void restoreContext(DataStream &stream, ContextMode mode) override
double giveEpsLoc() const
void updateYourself(TimeStep *tStep) override
FloatArrayF< 6 > plasticStrain
double tempVolumetricPlasticStrain
double kM
Elastic bulk modulus.
void initDamaged(double kappa, const FloatArrayF< 6 > &elasticStrain, GaussPoint *gp) const
ConcreteDPMStatus * giveConcreteDPMStatus(GaussPoint *gp) const
IsotropicLinearElasticMaterial linearElasticMaterial
Linear elastic material.
double mQ
The dilation parameter of the plastic potential.
double ASoft
Parameter of the ductilityMeasure of the damage model.
double computeDDKappaDDeltaLambdaDKappa(double sig, double rho, double theta, double tempKappa) const
std::tuple< double, double, double > computeTrialCoordinates(const FloatArrayF< 6 > &stress, GaussPoint *gp) const
Compute the trial coordinates.
void restoreConsistency(GaussPoint *gp) override
double computeDFDKappa(double sig, double rho, double theta, double tempKappa) const
double yieldTol
Yield tolerance for the plasticity model.
FloatArrayF< 6 > computeDCosThetaDStress(const FloatArrayF< 6 > &stress) const
Computes the derivative of costheta with respect to the stress.
double helem
Element size (to be used in fracture energy approach (crack band).
double computeHardeningOne(double tempKappa) const
FloatArrayF< 6 > giveRealStressVector_3d(const FloatArrayF< 6 > &strain, GaussPoint *gp, TimeStep *tStep) const override
Default implementation relies on giveRealStressVector for second Piola-Kirchoff stress.
void checkForVertexCase(double &answer, double sig, double tempKappa, GaussPoint *gp) const
FloatMatrixF< 6, 6 > computeDDRhoDDStress(const FloatArrayF< 6 > &stress) const
Computes the second derivative of rho with the respect to the stress.
std::unique_ptr< MaterialStatus > CreateStatus(GaussPoint *gp) const override
FloatMatrixF< 3, 3 > computeAMatrix(double sig, double rho, double theta, double tempKappa, double deltaLambda) const
double dilationConst
Control parameter for te volumetric plastic flow of the plastic potential.
FloatArrayF< 6 > computeDRhoDStress(const FloatArrayF< 6 > &stress) const
Computes the derivative of rho with respect to the stress.
void performVertexReturn(FloatArrayF< 6 > &stress, double apexStress, GaussPoint *gp) const
double gM
Elastic shear modulus.
double computeTempKappa(double kappaInitial, double sigTrial, double rhoTrial, double sig) const
FloatArrayF< 2 > computeDDKappaDDeltaLambdaDInv(double sig, double rho, double theta, double tempKappa) const
virtual double computeDuctilityMeasure(double sig, double rho, double theta) const
double computeYieldValue(double sig, double rho, double theta, double tempKappa) const
FloatMatrixF< 6, 6 > give3dMaterialStiffnessMatrix(MatResponseMode mode, GaussPoint *gp, TimeStep *tStep) const override
double computeDKappaDDeltaLambda(double sig, double rho, double theta, double tempKappa) const
double computeInverseDamage(double dam, GaussPoint *gp) const
Compute the damage-driving variable from given damage.
void restoreContext(DataStream &stream, ContextMode mode) override
void computeDSigDStress(FloatArrayF< 6 > &answer) const
Computes the derivative of sig with respect to the stress.
ConcreteDPM(int n, Domain *d)
Constructor.
void initializeFrom(InputRecord &ir) override
double AHard
Parameter of the ductilityMeasure of the plasticity model.
double computeRatioPotential(double sig, double tempKappa) const
int giveIPValue(FloatArray &answer, GaussPoint *gp, InternalStateType type, TimeStep *tStep) override
double nu
Elastic Poisson's ration.
double m
Plastic multiplier of the plasticity model.
double computeDuctilityMeasureDamage(const FloatArrayF< 6 > &strain, GaussPoint *gp) const
Compute the ductility measure for the damage model.
double ef
Hardening variable of plasticity model.
FloatArrayF< 2 > computeDDGDInvDKappa(double sig, double rho, double tempKappa) const
std::pair< double, double > computeDamage(const FloatArrayF< 6 > &strain, GaussPoint *gp, TimeStep *tStep) const
double CHard
Parameter of the ductilityMeasure of the plasticity model.
int newtonIter
Maximum number of iterations for stress return.
double computeDRDCosTheta(double theta, double ecc) const
Compute the derivative of R with respect to costheta.
FloatArrayF< 2 > computeDGDInv(double sig, double rho, double tempKappa) const
FloatArrayF< 2 > computeDDuctilityMeasureDInv(double sig, double rho, double theta, double tempKappa) const
FloatArrayF< 2 > computeDFDInv(double sig, double rho, double theta, double tempKappa) const
int setIPValue(const FloatArray &value, GaussPoint *gp, InternalStateType type) override
double href
Stress and its deviatoric part.
virtual double computeDamageParam(double kappa, GaussPoint *gp) const
Compute damage parameter.
void assignStateFlag(GaussPoint *gp) const
Assign state flag.
double computeHardeningOnePrime(double tempKappa) const
double DHard
Parameter of the ductilityMeasure of the plasticity model.
void performPlasticityReturn(GaussPoint *gp, FloatArrayF< 6 > &strain) const
virtual double computeEquivalentStrain(const FloatArrayF< 6 > &elasticStrain, GaussPoint *gp, TimeStep *tStep) const
Compute equivalent strain value.
double eM
Elastic Young's modulus.
double BHard
Parameter of the ductilityMeasure of the plasticity model.
double yieldHardInitial
Parameter of the hardening law of the plasticity model.
void saveContext(DataStream &stream, ContextMode mode) override
FloatMatrixF< 2, 2 > computeDDGDDInv(double sig, double rho, double tempKappa) const
void performRegularReturn(FloatArrayF< 6 > &stress, GaussPoint *gp, double theta) const
virtual int read(int *data, std::size_t count)=0
Reads count integer values into array pointed by data.
virtual int write(const int *data, std::size_t count)=0
Writes count integer values from array pointed by data.
virtual double giveCharacteristicLength(const FloatArray &normalToCrackPlane)
virtual void restoreContext(DataStream &stream, ContextMode mode)
virtual void saveContext(DataStream &stream, ContextMode mode)
double & at(std::size_t i)
int giveSize() const
Returns the size of receiver.
double dotProduct(const FloatArray &x) const
Index giveSize() const
Returns the size of receiver.
void zero()
Zeroes all coefficients of receiver.
Element * giveElement()
Returns corresponding element to receiver.
GaussPoint * gp
Associated integration point.
virtual MaterialStatus * giveStatus(GaussPoint *gp) const
Dictionary propertyDictionary
virtual double give(int aProperty, GaussPoint *gp) const
void initTempStatus() override
void printOutputAt(FILE *file, TimeStep *tStep) const override
Print receiver's output to given stream.
void saveContext(DataStream &stream, ContextMode mode) override
StructuralMaterialStatus(GaussPoint *g)
Constructor. Creates new StructuralMaterialStatus with IntegrationPoint g.
void updateYourself(TimeStep *tStep) override
FloatArray tempStrainVector
Temporary strain vector in reduced form (to find balanced state).
FloatArray tempStressVector
Temporary stress vector in reduced form (increments are used mainly in nonlinear analysis).
FloatArray stressVector
Equilibrated stress vector in reduced form.
FloatArray strainVector
Equilibrated strain vector in reduced form.
void restoreContext(DataStream &stream, ContextMode mode) override
static double computeThirdCoordinate(const FloatArrayF< 6 > &s)
static FloatArrayF< 6 > applyElasticStiffness(const FloatArrayF< 6 > &strain, double EModulus, double nu)
static FloatArrayF< 6 > applyElasticCompliance(const FloatArrayF< 6 > &stress, double EModulus, double nu)
static void computePrincipalValues(FloatArray &answer, const FloatArray &s, stressStrainPrincMode mode)
Common functions for convenience.
void initializeFrom(InputRecord &ir) override
StructuralMaterial(int n, Domain *d)
static FloatArrayF< 6 > computeDeviator(const FloatArrayF< 6 > &s)
static void computePrincipalValDir(FloatArray &answer, FloatMatrix &dir, const FloatArray &s, stressStrainPrincMode mode)
int setIPValue(const FloatArray &value, GaussPoint *gp, InternalStateType type) override
int giveIPValue(FloatArray &answer, GaussPoint *gp, InternalStateType type, TimeStep *tStep) override
static double computeSecondCoordinate(const FloatArrayF< 6 > &s)
static FloatArrayF< 6 > transformStressVectorTo(const FloatMatrixF< 3, 3 > &base, const FloatArrayF< 6 > &stress, bool transpose=false)
static std::pair< FloatArrayF< 6 >, double > computeDeviatoricVolumetricSplit(const FloatArrayF< 6 > &s)
FloatArrayF< 6 > computeStressIndependentStrainVector_3d(GaussPoint *gp, TimeStep *tStep, ValueModeType mode) const
#define DPM_DAMAGE_TOLERANCE
#define _IFT_ConcreteDPM_href
#define _IFT_ConcreteDPM_dhard
#define _IFT_ConcreteDPM_gf
#define _IFT_ConcreteDPM_fc
#define _IFT_ConcreteDPM_ft
#define _IFT_ConcreteDPM_ahard
#define _IFT_ConcreteDPM_yieldtol
#define _IFT_ConcreteDPM_bhard
#define _IFT_ConcreteDPM_dilation
#define _IFT_ConcreteDPM_ecc
#define _IFT_ConcreteDPM_asoft
#define _IFT_ConcreteDPM_chard
#define _IFT_ConcreteDPM_wf
#define _IFT_ConcreteDPM_newtoniter
#define _IFT_ConcreteDPM_helem
#define _IFT_ConcreteDPM_kinit
#define _IFT_IsotropicLinearElasticMaterial_n
#define _IFT_IsotropicLinearElasticMaterial_e
FloatMatrixF< N, M > dyad(const FloatArrayF< N > &a, const FloatArrayF< M > &b)
Computes the dyadic product .
FloatMatrixF< 3, 3 > from_voigt_strain_6(const FloatArrayF< 6 > &v)
FloatMatrixF< 3, 3 > from_voigt_stress_6(const FloatArrayF< 6 > &v)
FloatArrayF< N > solve(FloatMatrixF< N, N > mtrx, const FloatArrayF< N > &b, double zeropiv=1e-20)
double dot(const FloatArray &x, const FloatArray &y)
FloatMatrixF< N, N > inv(const FloatMatrixF< N, N > &mat, double zeropiv=1e-24)
Computes the inverse.
@ CIO_IOERR
General IO error.