3787 lines
195 KiB
C++
3787 lines
195 KiB
C++
|
|
|
|
// This file is part of the Herezh++ application.
|
|
//
|
|
// The finite element software Herezh++ is dedicated to the field
|
|
// of mechanics for large transformations of solid structures.
|
|
// It is developed by Gérard Rio (APP: IDDN.FR.010.0106078.000.R.P.2006.035.20600)
|
|
// INSTITUT DE RECHERCHE DUPUY DE LÔME (IRDL) <https://www.irdl.fr/>.
|
|
//
|
|
// Herezh++ is distributed under GPL 3 license ou ultérieure.
|
|
//
|
|
// Copyright (C) 1997-2021 Université Bretagne Sud (France)
|
|
// AUTHOR : Gérard Rio
|
|
// E-MAIL : gerardrio56@free.fr
|
|
//
|
|
// This program is free software: you can redistribute it and/or modify
|
|
// it under the terms of the GNU General Public License as published by
|
|
// the Free Software Foundation, either version 3 of the License,
|
|
// or (at your option) any later version.
|
|
//
|
|
// This program is distributed in the hope that it will be useful,
|
|
// but WITHOUT ANY WARRANTY; without even the implied warranty
|
|
// of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
|
// See the GNU General Public License for more details.
|
|
//
|
|
// You should have received a copy of the GNU General Public License
|
|
// along with this program. If not, see <https://www.gnu.org/licenses/>.
|
|
//
|
|
// For more information, please consult: <https://herezh.irdl.fr/>.
|
|
|
|
#include "Loi_comp_abstraite.h"
|
|
#include "Def_Umat.h"
|
|
#include "ExceptionsLoiComp.h"
|
|
#include "Util.h"
|
|
#include "TypeQuelconqueParticulier.h"
|
|
#include "CharUtil.h"
|
|
#include "TypeConsTens.h"
|
|
|
|
// CONSTRUCTEURS :
|
|
Loi_comp_abstraite::Loi_comp_abstraite () : // Constructeur par defaut
|
|
LoiAbstraiteGeneral(),saveResul(NULL),comp_tangent_simplifie(false)
|
|
,utilise_vitesse_deformation(false),type_de_deformation(DEFORMATION_STANDART)
|
|
,thermo_dependant(false),temperature_tdt(-1.),temperature_0(-1.),temperature_t(-1.)
|
|
,temperature(NULL),dilatation(false),def_en_cours(NULL)
|
|
,temps_loi()
|
|
,epsBB_totale(NULL),epsBB_therm(NULL)
|
|
,DepsBB_totale(NULL),DepsBB_therm(NULL),DepsBB_umat(NULL)
|
|
,listQuelc_mis_en_acces_localement(),listdeTouslesQuelc_dispo_localement()
|
|
,ptintmeca_en_cours(NULL),permet_affich_loi(0)
|
|
,permet_affich_loi_nD(NULL),li_quelconque(),tab_pt_li_quelconque()
|
|
{ };
|
|
// Constructeur utile si l'identificateur du nom de la loi
|
|
// de comportement et la dimension sont connus
|
|
Loi_comp_abstraite::Loi_comp_abstraite (Enum_comp id_compor,Enum_categorie_loi_comp categorie_comp
|
|
,int dimension,bool vit_def) :
|
|
LoiAbstraiteGeneral(id_compor,dimension,categorie_comp)
|
|
,saveResul(NULL),comp_tangent_simplifie(false)
|
|
,utilise_vitesse_deformation(vit_def),type_de_deformation(DEFORMATION_STANDART)
|
|
,thermo_dependant(false),temperature_tdt(-1.),temperature_0(-1.),temperature_t(-1.)
|
|
,temperature(NULL),dilatation(false),def_en_cours(NULL)
|
|
,temps_loi()
|
|
,epsBB_totale(NULL),epsBB_therm(NULL)
|
|
,DepsBB_totale(NULL),DepsBB_therm(NULL),DepsBB_umat(NULL)
|
|
,listQuelc_mis_en_acces_localement(),listdeTouslesQuelc_dispo_localement()
|
|
,ptintmeca_en_cours(NULL),permet_affich_loi(0)
|
|
,permet_affich_loi_nD(NULL),li_quelconque(),tab_pt_li_quelconque()
|
|
{ };
|
|
|
|
// Constructeur utile si l'identificateur du nom de la loi
|
|
// de comportement et la dimension sont connus
|
|
Loi_comp_abstraite::Loi_comp_abstraite (char* nom,Enum_categorie_loi_comp categorie_comp
|
|
,int dimension,bool vit_def) :
|
|
LoiAbstraiteGeneral(nom,dimension,categorie_comp)
|
|
,saveResul(NULL),comp_tangent_simplifie(false)
|
|
,utilise_vitesse_deformation(vit_def),type_de_deformation(DEFORMATION_STANDART)
|
|
,thermo_dependant(false),temperature_tdt(-1.),temperature_0(-1.),temperature_t(-1.)
|
|
,temperature(NULL),dilatation(false),def_en_cours(NULL)
|
|
,temps_loi()
|
|
,epsBB_totale(NULL),epsBB_therm(NULL)
|
|
,DepsBB_totale(NULL),DepsBB_therm(NULL),DepsBB_umat(NULL)
|
|
,listQuelc_mis_en_acces_localement(),listdeTouslesQuelc_dispo_localement()
|
|
,ptintmeca_en_cours(NULL),permet_affich_loi(0)
|
|
,permet_affich_loi_nD(NULL),li_quelconque(),tab_pt_li_quelconque()
|
|
|
|
{ };
|
|
|
|
// Constructeur de copie
|
|
Loi_comp_abstraite::Loi_comp_abstraite (const Loi_comp_abstraite & a ) :
|
|
LoiAbstraiteGeneral(a),comp_tangent_simplifie(false)
|
|
,utilise_vitesse_deformation(a.utilise_vitesse_deformation)
|
|
// ,saveResul(a.saveResul->Nevez_SaveResul()),type_de_deformation(a.type_de_deformation)
|
|
,saveResul(a.saveResul),type_de_deformation(a.type_de_deformation)
|
|
,thermo_dependant(a.thermo_dependant),dilatation(a.dilatation)
|
|
,def_en_cours(a.def_en_cours)
|
|
,temps_loi(a.temps_loi)
|
|
,temperature_tdt(-1.),temperature_0(-1.),temperature_t(-1.),temperature(NULL)
|
|
,epsBB_totale(NULL),epsBB_therm(NULL)
|
|
,DepsBB_totale(NULL),DepsBB_therm(NULL),DepsBB_umat(NULL)
|
|
,listQuelc_mis_en_acces_localement(a.listQuelc_mis_en_acces_localement)
|
|
,listdeTouslesQuelc_dispo_localement(a.listdeTouslesQuelc_dispo_localement)
|
|
,ptintmeca_en_cours(NULL),permet_affich_loi(a.permet_affich_loi)
|
|
,permet_affich_loi_nD(a.permet_affich_loi_nD)
|
|
,li_quelconque(a.li_quelconque),tab_pt_li_quelconque()
|
|
|
|
{ // idem pour les fonctions nD
|
|
if (permet_affich_loi_nD != NULL)
|
|
{if (permet_affich_loi_nD->NomFonction() == "_")
|
|
{// comme il s'agit d'une fonction locale on la redéfinie (sinon pb lors du destructeur de loi)
|
|
string non_courbe("_");
|
|
permet_affich_loi_nD = Fonction_nD::New_Fonction_nD(*a.permet_affich_loi_nD);
|
|
};
|
|
// on s'occupe maintenant des stockages des grandeurs complètement quelconques
|
|
// qui seront nécessaire pour utiliser la fonction nD
|
|
// !! on considère que a.li_quelconque a bien été dimensionné en fonction de
|
|
// permet_affich_loi_nD, donc on ne fait que bien définir les pointeurs
|
|
if (li_quelconque.size())
|
|
{tab_pt_li_quelconque.Change_taille(li_quelconque.size());
|
|
List_io <TypeQuelconque >::iterator ili,ilifin = li_quelconque.end();
|
|
int i=1; // init
|
|
for (ili= li_quelconque.begin();ili != ilifin; ili++,i++)
|
|
tab_pt_li_quelconque(i) = &(*ili);
|
|
};
|
|
};
|
|
} ;
|
|
|
|
// DESTRUCTEUR VIRTUEL :
|
|
Loi_comp_abstraite::~Loi_comp_abstraite ()
|
|
{ if (epsBB_totale != NULL) delete epsBB_totale;
|
|
if (epsBB_therm != NULL) delete epsBB_therm;
|
|
if (DepsBB_totale != NULL) delete DepsBB_totale;
|
|
if (DepsBB_therm != NULL) delete DepsBB_therm;
|
|
if (DepsBB_umat != NULL) delete DepsBB_umat;
|
|
if (permet_affich_loi_nD != NULL)
|
|
if (permet_affich_loi_nD->NomFonction() == "_") delete permet_affich_loi_nD;
|
|
};
|
|
|
|
|
|
// =============== methode de calcul ======================
|
|
|
|
// définition du type de calcul de déformation sur une instance de déformation passée en paramètre
|
|
void Loi_comp_abstraite::Def_type_deformation(Deformation & def)
|
|
{ def.Change_type_de_deformation(type_de_deformation);
|
|
};
|
|
|
|
// schema de calcul explicite à t
|
|
const Met_abstraite::Expli& Loi_comp_abstraite::Cal_explicit_t
|
|
(Loi_comp_abstraite::SaveResul * saveDon
|
|
,Deformation & def,DdlElement & tab_ddl,PtIntegMecaInterne& ptintmeca,Tableau <TenseurBB *> & d_epsBB
|
|
,double& jacobien,CompThermoPhysiqueAbstraite::SaveResul * saveTP,CompThermoPhysiqueAbstraite* loiTP
|
|
,bool dilat,EnergieMeca & energ,const EnergieMeca & energ_t,bool premier_calcul
|
|
)
|
|
{
|
|
Temps_CPU_HZpp& temps_cpu_loi = ptintmeca.Tps_cpu_loi_comp();
|
|
temps_cpu_loi.Mise_en_route_du_comptage(); // spécifique pti
|
|
temps_loi.Mise_en_route_du_comptage(); // spécifique loi
|
|
// passage des infos specifiques aux classes derivantes
|
|
saveResul = saveDon;
|
|
def_en_cours = &def;
|
|
// récup des contraintes
|
|
TenseurHH & sigHH_t = *(ptintmeca.SigHH_t());
|
|
TenseurHH & sigHH = *(ptintmeca.SigHH());
|
|
TenseurBB & epsBB_t = *(ptintmeca.EpsBB());
|
|
TenseurBB & DepsBB_ = *(ptintmeca.DepsBB());
|
|
TenseurBB & DeltaEpsBB_ = *(ptintmeca.DeltaEpsBB());
|
|
double& module_compressibilite = ptintmeca.ModuleCompressibilite();
|
|
double& module_cisaillement = ptintmeca.ModuleCisaillement();
|
|
Tableau <double>& def_equi = ptintmeca.Deformation_equi();
|
|
const Tableau <double>& def_equi_t = ptintmeca.Deformation_equi_t_const();
|
|
dilatation=dilat;
|
|
ptintmeca_en_cours = &ptintmeca; // pour les méthodes internes
|
|
|
|
// calcul de : epsBB_t,gijBB_t, gijHH_t,d_epsBB,jacobien
|
|
Temps_CPU_HZpp& temps_cpu_metrique = ptintmeca.TpsMetrique();
|
|
temps_cpu_metrique.Mise_en_route_du_comptage(); // cpu
|
|
const Met_abstraite::Expli& ex = def.Cal_explicit_t(def_equi_t,epsBB_t,d_epsBB,def_equi,DepsBB_,DeltaEpsBB_,premier_calcul);
|
|
// on récupère les positions des points
|
|
if (premier_calcul)
|
|
{ptintmeca.M_0() = def.Position_0();
|
|
ptintmeca.M_t() = def.Position_t();
|
|
};
|
|
ptintmeca.M_tdt() = def.Position_tdt();
|
|
temps_cpu_metrique.Arret_du_comptage(); // cpu
|
|
// dans le cas d'une loi thermo dépendante, calcul de la température
|
|
if ((thermo_dependant) || dilatation)
|
|
{temperature_0 = def.DonneeInterpoleeScalaire(TEMP,TEMPS_0);
|
|
temperature_t = def.DonneeInterpoleeScalaire(TEMP,TEMPS_t);
|
|
temperature = &temperature_t;
|
|
};
|
|
// dans le cas ou l'on tiens compte de la dilatation on modifie les différents tenseurs de déformation
|
|
ThermoDonnee dTP; // init à 0 par défaut
|
|
if (dilatation)
|
|
{ // attention ici ça peut donner 0 car le pas précédent c'est peut-être 0
|
|
// comme on n'en sait rien on fait comme si il y a une valeur déjà enregistrée: pas terrible !!!
|
|
// vu que sigma suivant dépend de epsméca et que epsmeca dépend de sigma !!!
|
|
double P = -(sigHH_t * (*(ex.gijBB_t))).Trace()/Abs(sigHH_t.Dimension()); // calcul de la pression
|
|
loiTP->Cal_donnees_thermiques(P,saveTP,def,P,TEMPS_t,dTP);
|
|
// modification de la déformation mécanique et calcul de la déformation thermique
|
|
// a- dimensionnement des tenseurs intermédiaires qui pour l'instant ne servent qu'ici
|
|
int dim_tens = epsBB_t.Dimension();
|
|
// -- cas de la déformation
|
|
if (epsBB_totale == NULL) { epsBB_totale = NevezTenseurBB(dim_tens);}
|
|
else if (epsBB_totale->Dimension() != dim_tens) { delete epsBB_totale;epsBB_totale = NevezTenseurBB(dim_tens);};
|
|
*epsBB_totale = epsBB_t;
|
|
if (epsBB_therm == NULL) { epsBB_therm = NevezTenseurBB(dim_tens);}
|
|
else if (epsBB_therm->Dimension() != dim_tens) { delete epsBB_therm;epsBB_therm = NevezTenseurBB(dim_tens);};
|
|
// -- cas de la vitesse de déformation
|
|
if (DepsBB_totale == NULL) { DepsBB_totale = NevezTenseurBB(dim_tens);}
|
|
else if (DepsBB_totale->Dimension() != dim_tens) { delete DepsBB_totale;DepsBB_totale = NevezTenseurBB(dim_tens);};
|
|
*DepsBB_totale = DepsBB_;
|
|
if (DepsBB_therm == NULL) { DepsBB_therm = NevezTenseurBB(dim_tens);}
|
|
else if (DepsBB_therm->Dimension() != dim_tens) { delete DepsBB_therm;DepsBB_totale = NevezTenseurBB(dim_tens);};
|
|
// -- calcul du partage entre thermique et mécanique
|
|
bool avec_repercution_sur_def_meca = true;
|
|
def.DeformationThermoMecanique(temperature_0,*(ex.gijBB_t),dTP,*epsBB_totale
|
|
,*epsBB_therm,temperature_t,epsBB_t,temperature_t
|
|
,*DepsBB_totale,*DepsBB_therm,DepsBB_,false,avec_repercution_sur_def_meca);
|
|
};
|
|
if ((thermo_dependant) || dilatation) // répercussion éventuelle du changement de température dans les classes dérivées
|
|
{ RepercuteChangeTemperature(TEMPS_t); };
|
|
// calcul éventuel des invariants liés à la cinématique
|
|
CalculInvariants_cinematique(ptintmeca,*(ex.gijBB_t),*(ex.gijHH_t));
|
|
// demande dans les classes dérivées du calcul de grandeurs spécifiques si besoin est
|
|
// opération de transmission de la métrique
|
|
const Met_abstraite::Impli* ex_impli = NULL;
|
|
const Met_abstraite::Expli_t_tdt inter_ex_tdt = ex.T_dans_tdt();
|
|
const Met_abstraite::Expli_t_tdt* ex_expli_tdt = &inter_ex_tdt;
|
|
const Met_abstraite::Umat_cont* ex_expli = NULL;
|
|
CalculGrandeurTravail(ptintmeca,def,TEMPS_t,dTP,ex_impli,ex_expli_tdt,ex_expli,NULL,NULL);
|
|
// calcul de : sigHH
|
|
// on utilise la fonction qui calcul à t+dt en mettant les grandeur à t de l'appel idem ceux à t+dt
|
|
// pour l'instant (si pb on verra)
|
|
// on utilise lafonction T_dans_tdt pour passer avec une grandeur Expli_t_tdt au lieu de Expli
|
|
// c'est clair que ce n'est pas très cohérent, pour l'instant on laisse car cette fonction ne sert pas
|
|
// on gère les exceptions éventuelles en mettant le bloc sous surveillance
|
|
try
|
|
{ Calcul_SigmaHH (sigHH_t,DepsBB_,tab_ddl,*(ex.gijBB_t),*(ex.gijHH_t),*(ex.giB_t),*(ex.giH_t),
|
|
epsBB_t,DeltaEpsBB_,*(ex.gijBB_t),*(ex.gijHH_t),*(ex.d_gijBB_t),
|
|
(*ex.jacobien_0),(*ex.jacobien_t),sigHH,energ,energ_t
|
|
,module_compressibilite,module_cisaillement,ex.T_dans_tdt());
|
|
}
|
|
catch (ErrSortieFinale)
|
|
// cas d'une direction voulue vers la sortie
|
|
// on relance l'interuption pour le niveau supérieur
|
|
{ ErrSortieFinale toto;
|
|
throw (toto);
|
|
}
|
|
catch ( ... ) // cas d'une erreur dans la recherche de la contrainte
|
|
{ throw ErrNonConvergence_loiDeComportement();
|
|
if (ParaGlob::NiveauImpression() >= 1)
|
|
cout << "\n warning: exception generee par la loi de comportement ";
|
|
if (ParaGlob::NiveauImpression() >= 4) cout << "\n Loi_comp_abstraite::Cal_explicit_t(..";
|
|
};
|
|
jacobien = (*ex.jacobien_t);
|
|
// calcul éventuel des invariants de contraintes
|
|
CalculInvariants_contraintes(ptintmeca,*(ex.gijBB_t),*(ex.gijHH_t));
|
|
|
|
// en sortie il nous faut définir d_epsBB qui doit être égale à D*, donc pas forcément la dérivée
|
|
// de epsBB (par exemple dans le cas de la déformation logarithmique ou cumulée)
|
|
// variation de la déformation / au ddl
|
|
if (type_de_deformation != DEFORMATION_STANDART)
|
|
{ int d_epsBBTaille = d_epsBB.Taille();
|
|
for (int i=1; i<= d_epsBBTaille; i++)
|
|
*(d_epsBB(i)) = 0.5 * (*((*(ex.d_gijBB_t))(i)));
|
|
};
|
|
def_en_cours=NULL; // plus d'accès possible à la sortie
|
|
ptintmeca_en_cours = NULL; // plus d'accès possible à la sortie
|
|
temps_cpu_loi.Arret_du_comptage(); // cpu spécifique pti
|
|
temps_loi.Arret_du_comptage(); // cpu spécifique loi
|
|
return ex; // retour de la métrique
|
|
};
|
|
|
|
|
|
// schema de calcul explicite à tdt
|
|
const Met_abstraite::Expli_t_tdt& Loi_comp_abstraite::Cal_explicit_tdt
|
|
(Loi_comp_abstraite::SaveResul * saveDon,Deformation & def
|
|
,DdlElement & tab_ddl
|
|
,PtIntegMecaInterne& ptintmeca,Tableau <TenseurBB *> & d_epsBB,double& jacobien
|
|
,CompThermoPhysiqueAbstraite::SaveResul * saveTP,CompThermoPhysiqueAbstraite* loiTP
|
|
,bool dilat,EnergieMeca & energ,const EnergieMeca & energ_t,bool premier_calcul
|
|
)
|
|
{
|
|
Temps_CPU_HZpp& temps_cpu_loi = ptintmeca.Tps_cpu_loi_comp();
|
|
temps_cpu_loi.Mise_en_route_du_comptage(); // spécifique pti
|
|
temps_loi.Mise_en_route_du_comptage(); // spécifique loi
|
|
// passage des infos specifiques aux classes derivantes
|
|
saveResul = saveDon;
|
|
def_en_cours = &def;
|
|
// récup des contraintes
|
|
TenseurHH & sigHH = *(ptintmeca.SigHH()); // ici _tdt est la grandeur finale
|
|
TenseurHH & sigHH_t = *(ptintmeca.SigHH_t()); // ici _tdt est la grandeur finale
|
|
TenseurBB & epsBB_tdt = *(ptintmeca.EpsBB());
|
|
TenseurBB & DepsBB_ = *(ptintmeca.DepsBB());
|
|
TenseurBB & delta_epsBB = *(ptintmeca.DeltaEpsBB());
|
|
double& module_compressibilite = ptintmeca.ModuleCompressibilite();
|
|
double& module_cisaillement = ptintmeca.ModuleCisaillement();
|
|
Tableau <double>& def_equi = ptintmeca.Deformation_equi();
|
|
Tableau <double>& def_equi_t = ptintmeca.Deformation_equi_t();
|
|
dilatation=dilat;
|
|
ptintmeca_en_cours = &ptintmeca; // pour les méthodes internes
|
|
|
|
// calcul de : epsBB_t,gijBB_tdt, gijHH_tdt,d_epsBB,jacobien
|
|
Temps_CPU_HZpp& temps_cpu_metrique = ptintmeca.TpsMetrique();
|
|
temps_cpu_metrique.Mise_en_route_du_comptage(); // cpu
|
|
const Met_abstraite::Expli_t_tdt& ex = def.Cal_explicit_tdt(def_equi_t,epsBB_tdt,d_epsBB,def_equi,DepsBB_,delta_epsBB,premier_calcul);
|
|
// on récupère les positions des points
|
|
if (premier_calcul)
|
|
{ptintmeca.M_0() = def.Position_0();
|
|
ptintmeca.M_t() = def.Position_t();
|
|
};
|
|
ptintmeca.M_tdt() = def.Position_tdt();
|
|
temps_cpu_metrique.Arret_du_comptage(); // cpu
|
|
// dans le cas d'une loi thermo dépendante, calcul de la température
|
|
if ((thermo_dependant) || dilatation)
|
|
{temperature_0 = def.DonneeInterpoleeScalaire(TEMP,TEMPS_0);
|
|
temperature_t = def.DonneeInterpoleeScalaire(TEMP,TEMPS_t);
|
|
temperature_tdt = def.DonneeInterpoleeScalaire(TEMP,TEMPS_tdt);
|
|
temperature = &temperature_tdt;
|
|
};
|
|
// dans le cas ou l'on tiens compte de la dilatation on modifie les différents tenseurs de déformation
|
|
ThermoDonnee dTP; // init à 0 par défaut
|
|
if (dilatation)
|
|
{ // attention ici la seule valeur disponible est la contrainte du temps précédent
|
|
// donc pour des questions d'erreur de transport de la contrainte, on utilise également la métrique au pas précédent
|
|
double P = -(sigHH_t * (*(ex.gijBB_t))).Trace()/Abs(sigHH_t.Dimension()); // calcul de la pression
|
|
loiTP->Cal_donnees_thermiques(P,saveTP,def,P,TEMPS_tdt,dTP);
|
|
// modification de la déformation mécanique et calcul de la déformation thermique
|
|
// a- dimensionnement des tenseurs intermédiaires qui pour l'instant ne servent qu'ici
|
|
int dim_tens = epsBB_tdt.Dimension();
|
|
// -- cas de la déformation
|
|
if (epsBB_totale == NULL) { epsBB_totale = NevezTenseurBB(dim_tens);}
|
|
else if (epsBB_totale->Dimension() != dim_tens) { delete epsBB_totale;epsBB_totale = NevezTenseurBB(dim_tens);};
|
|
*epsBB_totale = epsBB_tdt;
|
|
if (epsBB_therm == NULL) { epsBB_therm = NevezTenseurBB(dim_tens);}
|
|
else if (epsBB_therm->Dimension() != dim_tens) { delete epsBB_therm;epsBB_therm = NevezTenseurBB(dim_tens);};
|
|
// -- cas de la vitesse de déformation
|
|
if (DepsBB_totale == NULL) { DepsBB_totale = NevezTenseurBB(dim_tens);}
|
|
else if (DepsBB_totale->Dimension() != dim_tens) { delete DepsBB_totale;DepsBB_totale = NevezTenseurBB(dim_tens);};
|
|
*DepsBB_totale = DepsBB_;
|
|
if (DepsBB_therm == NULL) { DepsBB_therm = NevezTenseurBB(dim_tens);}
|
|
else if (DepsBB_therm->Dimension() != dim_tens) { delete DepsBB_therm;DepsBB_totale = NevezTenseurBB(dim_tens);};
|
|
// -- calcul du partage entre thermique et mécanique
|
|
bool avec_repercution_sur_def_meca = true;
|
|
def.DeformationThermoMecanique(temperature_0,*(ex.gijBB_tdt),dTP,*epsBB_totale
|
|
,*epsBB_therm,temperature_tdt,epsBB_tdt,temperature_t
|
|
,*DepsBB_totale,*DepsBB_therm,DepsBB_,true,avec_repercution_sur_def_meca);
|
|
};
|
|
if ((thermo_dependant) || dilatation) // répercussion éventuelle du changement de température dans les classes dérivées
|
|
{ RepercuteChangeTemperature(TEMPS_tdt); };
|
|
// calcul éventuel des invariants liés à la cinématique
|
|
CalculInvariants_cinematique(ptintmeca,*(ex.gijBB_t),*(ex.gijHH_t));
|
|
// demande dans les classes dérivées du calcul de grandeurs spécifiques si besoin est
|
|
const Met_abstraite::Impli* ex_impli = NULL;
|
|
const Met_abstraite::Expli_t_tdt* ex_expli_tdt = &ex;
|
|
const Met_abstraite::Umat_cont* ex_expli = NULL;
|
|
CalculGrandeurTravail(ptintmeca,def,TEMPS_tdt,dTP,ex_impli,ex_expli_tdt,ex_expli,NULL,NULL);
|
|
// calcul de : sigHH
|
|
// on gère les exceptions éventuelles en mettant le bloc sous surveillance
|
|
try
|
|
{ Calcul_SigmaHH (sigHH_t,DepsBB_,tab_ddl,*(ex.gijBB_t),*(ex.gijHH_t),*(ex.giB_tdt),*(ex.giH_tdt),
|
|
epsBB_tdt,delta_epsBB,*(ex.gijBB_tdt),*(ex.gijHH_tdt),*(ex.d_gijBB_tdt),
|
|
(*ex.jacobien_0),(*ex.jacobien_tdt),sigHH,energ,energ_t
|
|
,module_compressibilite,module_cisaillement,ex);
|
|
//--- debug
|
|
//cout << "\n sigHH.MaxiComposante() "<<sigHH.MaxiComposante();
|
|
//if (sigHH.MaxiComposante() > 20.)
|
|
// { cout << "\n debug .... Loi_comp_abstraite::Cal_explicit_tdt "
|
|
// << "\n **** sigHH.MaxiComposante() > 20. ";
|
|
//
|
|
// TenseurBB* ptBB = NevezTenseurBB(epsBB_tdt);
|
|
// epsBB_tdt.BaseAbsolue(*ptBB,*(ex.giH_tdt));
|
|
// cout << "\n eps: ";
|
|
// ptBB->Ecriture(cout);
|
|
// delta_epsBB.BaseAbsolue(*ptBB,*(ex.giH_tdt));
|
|
// cout << "\n delta eps: ";
|
|
// ptBB->Ecriture(cout);
|
|
// TenseurHH* ptHH = NevezTenseurHH(sigHH);
|
|
// sigHH.BaseAbsolue(*ptHH,*(ex.giB_tdt));
|
|
// cout << "\n sigma: ";
|
|
// ptHH->Ecriture(cout);
|
|
// delete ptBB; delete ptHH;
|
|
//
|
|
//
|
|
// // on recalcule pour le debug le vecteur résidu
|
|
// Calcul_SigmaHH (sigHH_t,DepsBB_,tab_ddl,*(ex.gijBB_t),*(ex.gijHH_t),*(ex.giB_tdt),*(ex.giH_tdt),
|
|
// epsBB_tdt,delta_epsBB,*(ex.gijBB_tdt),*(ex.gijHH_tdt),*(ex.d_gijBB_tdt),
|
|
// (*ex.jacobien_0),(*ex.jacobien_tdt),sigHH,energ,energ_t
|
|
// ,module_compressibilite,module_cisaillement,ex);
|
|
// };
|
|
|
|
//--- fin debug
|
|
}
|
|
catch (ErrSortieFinale)
|
|
// cas d'une direction voulue vers la sortie
|
|
// on relance l'interuption pour le niveau supérieur
|
|
{ ErrSortieFinale toto;
|
|
throw (toto);
|
|
}
|
|
catch ( ... ) // cas d'une erreur dans la recherche de la contrainte
|
|
{ throw ErrNonConvergence_loiDeComportement();
|
|
if (ParaGlob::NiveauImpression() >= 1)
|
|
cout << "\n warning: exception generee par la loi de comportement ";
|
|
if (ParaGlob::NiveauImpression() >= 4) cout << "\n Loi_comp_abstraite::Cal_explicit_tdt(..";
|
|
};
|
|
jacobien = (*ex.jacobien_tdt);
|
|
// calcul éventuel des invariants de contraintes
|
|
CalculInvariants_contraintes(ptintmeca,*(ex.gijBB_tdt),*(ex.gijHH_tdt));
|
|
// en sortie il nous faut définir d_epsBB qui doit être égale à D*, donc pas forcément la dérivée
|
|
// de epsBB (par exemple dans le cas de la déformation logarithmique ou cumulée)
|
|
// variation de la déformation / au ddl
|
|
if (type_de_deformation != DEFORMATION_STANDART)
|
|
{ int d_epsBBTaille = d_epsBB.Taille();
|
|
for (int i=1; i<= d_epsBBTaille; i++)
|
|
*(d_epsBB(i)) = 0.5 * (*((*(ex.d_gijBB_tdt))(i)));
|
|
};
|
|
def_en_cours=NULL; // plus d'accès possible à la sortie
|
|
ptintmeca_en_cours = NULL; // plus d'accès possible à la sortie
|
|
temps_cpu_loi.Arret_du_comptage(); // cpu spécifique pti
|
|
temps_loi.Arret_du_comptage(); // cpu spécifique loi
|
|
// retour
|
|
return ex; // retour de la métrique
|
|
};
|
|
|
|
// schema implicit
|
|
const Met_abstraite::Impli& Loi_comp_abstraite::Cal_implicit
|
|
(Loi_comp_abstraite::SaveResul * saveDon
|
|
,Deformation & def,DdlElement & tab_ddl,PtIntegMecaInterne & ptintmeca
|
|
, Tableau <TenseurBB *>& d_epsBB_tdt,double& jacobien,Vecteur& d_jacobien_tdt
|
|
,Tableau <TenseurHH *>& d_sigHH,const ParaAlgoControle &
|
|
,CompThermoPhysiqueAbstraite::SaveResul * saveTP,CompThermoPhysiqueAbstraite* loiTP
|
|
,bool dilat,EnergieMeca & energ,const EnergieMeca & energ_t,bool premier_calcul
|
|
)
|
|
{
|
|
Temps_CPU_HZpp& temps_cpu_loi = ptintmeca.Tps_cpu_loi_comp();
|
|
temps_cpu_loi.Mise_en_route_du_comptage(); // spécifique pti
|
|
temps_loi.Mise_en_route_du_comptage(); // spécifique loi
|
|
// passage des infos specifiques aux classes derivantes
|
|
saveResul = saveDon;
|
|
def_en_cours=&def;
|
|
|
|
// récup des contraintes
|
|
TenseurHH & sigHH = *(ptintmeca.SigHH()); // ici _tdt est la grandeur finale
|
|
TenseurHH & sigHH_t = *(ptintmeca.SigHH_t()); // ici _tdt est la grandeur finale
|
|
TenseurBB & epsBB_tdt = *(ptintmeca.EpsBB());
|
|
TenseurBB & DepsBB_ = *(ptintmeca.DepsBB());
|
|
TenseurBB & delta_epsBB = *(ptintmeca.DeltaEpsBB());
|
|
double& module_compressibilite = ptintmeca.ModuleCompressibilite();
|
|
double& module_cisaillement = ptintmeca.ModuleCisaillement();
|
|
Tableau <double>& def_equi = ptintmeca.Deformation_equi();
|
|
const Tableau <double>& def_equi_t = ptintmeca.Deformation_equi_t_const();
|
|
dilatation=dilat;
|
|
ptintmeca_en_cours = &ptintmeca; // pour les méthodes internes
|
|
|
|
// calcul de : epsBB_tdt, delta_epsBB,gijBB_tdt, gijHH_tdt, d_gijBB_tdt,
|
|
// d_gijHH_tdt,jacobien,d_jacobien_tdt
|
|
Temps_CPU_HZpp& temps_cpu_metrique = ptintmeca.TpsMetrique();
|
|
temps_cpu_metrique.Mise_en_route_du_comptage(); // cpu
|
|
bool calcul_varD_ddl = utilise_vitesse_deformation;
|
|
const Met_abstraite::Impli& ex = def.Cal_implicit(def_equi_t,epsBB_tdt,d_epsBB_tdt,def_equi,DepsBB_
|
|
,delta_epsBB,premier_calcul);
|
|
|
|
//------- affichage d'erreurs éventuelles ----
|
|
bool sortie_metrique = false; // pour ne pas afficher 2 fois
|
|
if (Permet_affichage() > 2)
|
|
{ // on regarde la taille des déformations
|
|
double maxgijBB = ex.gijBB_tdt->MaxiComposante();
|
|
if (( maxgijBB > ConstMath::grand)
|
|
|| (!isfinite(maxgijBB)) || (isnan(maxgijBB))
|
|
)
|
|
sortie_metrique = true;
|
|
|
|
double maxepsBB_tdt = epsBB_tdt.MaxiComposante();
|
|
if (( maxepsBB_tdt > ConstMath::grand)
|
|
|| (!isfinite(maxepsBB_tdt)) || (isnan(maxepsBB_tdt))
|
|
)
|
|
sortie_metrique = true;
|
|
|
|
double maxgijHH = ex.gijHH_tdt->MaxiComposante();
|
|
if (( maxgijHH > ConstMath::grand)
|
|
|| (!isfinite(maxgijHH)) || (isnan(maxgijHH))
|
|
)
|
|
sortie_metrique = true;
|
|
|
|
if (!sortie_metrique) // on peut donc tester une division
|
|
{ double maxgijBB_0 = ex.gijBB_0->MaxiComposante();
|
|
double ratio1 = maxgijBB/maxgijBB_0;
|
|
if ( (ratio1 > 1000.) || (ratio1 < 0.001))
|
|
sortie_metrique = true;
|
|
double maxgijHH_0 = ex.gijHH_0->MaxiComposante();
|
|
double ratio2 = maxgijHH/maxgijHH_0;
|
|
if ( (ratio2 > 1000.) || (ratio2 < 0.001))
|
|
sortie_metrique = true;
|
|
};
|
|
|
|
if ((sortie_metrique) || (Permet_affichage() > 8))
|
|
def.Affiche();
|
|
};
|
|
|
|
// on récupère les positions des points
|
|
if (premier_calcul)
|
|
{ptintmeca.M_0() = def.Position_0();
|
|
ptintmeca.M_t() = def.Position_t();
|
|
};
|
|
ptintmeca.M_tdt() = def.Position_tdt();
|
|
temps_cpu_metrique.Arret_du_comptage(); // cpu
|
|
|
|
// dans le cas d'une loi thermo dépendante, calcul de la température
|
|
if ((thermo_dependant) || dilatation)
|
|
{temperature_0 = def.DonneeInterpoleeScalaire(TEMP,TEMPS_0);
|
|
temperature_t = def.DonneeInterpoleeScalaire(TEMP,TEMPS_t);
|
|
temperature_tdt = def.DonneeInterpoleeScalaire(TEMP,TEMPS_tdt);
|
|
temperature = &temperature_tdt;
|
|
};
|
|
// demande dans les classes dérivées du calcul de grandeurs spécifiques si besoin est
|
|
// dans le cas ou l'on tiens compte de la dilatation on modifie les différents tenseurs de déformation
|
|
ThermoDonnee dTP; // init à 0 par défaut
|
|
if (dilatation)
|
|
{ // attention ici on utilise la contrainte du temps précédent, il pourrait y avoir des oscillations
|
|
// vu que sigma suivant dépend de epsméca et que epsmeca dépend de sigma !!!
|
|
// double P = -(sigHH_t * (*(ex.gijBB_tdt))).Trace()/Abs(sigHH_t.Dimension()); // calcul de la pression
|
|
// on utilise la valeur à tdt, qui est donc celle calculée à l'itération précédente en implicite
|
|
double P = -(sigHH * (*(ex.gijBB_tdt))).Trace()/Abs(sigHH.Dimension()); // calcul de la pression
|
|
// et celle du pas précédent
|
|
double P_t = -(sigHH_t * (*(ex.gijBB_t))).Trace()/Abs(sigHH_t.Dimension()); // calcul de la pression à t
|
|
loiTP->Cal_donnees_thermiques(P_t,saveTP,def,P,TEMPS_tdt,dTP);
|
|
// modification de la déformation mécanique et calcul de la déformation thermique
|
|
// a- dimensionnement des tenseurs intermédiaires qui pour l'instant ne servent qu'ici
|
|
int dim_tens = epsBB_tdt.Dimension();
|
|
// -- cas de la déformation
|
|
if (epsBB_totale == NULL) { epsBB_totale = NevezTenseurBB(dim_tens);}
|
|
else if (epsBB_totale->Dimension() != dim_tens) { delete epsBB_totale;epsBB_totale = NevezTenseurBB(dim_tens);};
|
|
*epsBB_totale = epsBB_tdt;
|
|
if (epsBB_therm == NULL) { epsBB_therm = NevezTenseurBB(dim_tens);}
|
|
else if (epsBB_therm->Dimension() != dim_tens) { delete epsBB_therm;epsBB_therm = NevezTenseurBB(dim_tens);};
|
|
// -- cas de la vitesse de déformation
|
|
if (DepsBB_totale == NULL) { DepsBB_totale = NevezTenseurBB(dim_tens);}
|
|
else if (DepsBB_totale->Dimension() != dim_tens) { delete DepsBB_totale;DepsBB_totale = NevezTenseurBB(dim_tens);};
|
|
*DepsBB_totale = DepsBB_;
|
|
if (DepsBB_therm == NULL) { DepsBB_therm = NevezTenseurBB(dim_tens);}
|
|
else if (DepsBB_therm->Dimension() != dim_tens) { delete DepsBB_therm;DepsBB_totale = NevezTenseurBB(dim_tens);};
|
|
// -- calcul du partage entre thermique et mécanique
|
|
bool avec_repercution_sur_def_meca = true;
|
|
def.DeformationThermoMecanique(temperature_0,*(ex.gijBB_tdt),dTP,*epsBB_totale
|
|
,*epsBB_therm,temperature_tdt,epsBB_tdt,temperature_t
|
|
,*DepsBB_totale,*DepsBB_therm,DepsBB_,true,avec_repercution_sur_def_meca);
|
|
};
|
|
if ((thermo_dependant) || dilatation) // répercussion éventuelle du changement de température dans les classes dérivées
|
|
{ RepercuteChangeTemperature(TEMPS_tdt); };
|
|
// calcul éventuel des invariants liés à la cinématique
|
|
CalculInvariants_cinematique(ptintmeca,*(ex.gijBB_t),*(ex.gijHH_t));
|
|
// demande dans les classes dérivées du calcul de grandeurs spécifiques si besoin est
|
|
const Met_abstraite::Impli* ex_impli = &ex;
|
|
const Met_abstraite::Expli_t_tdt* ex_expli_tdt = NULL;
|
|
const Met_abstraite::Umat_cont* ex_expli = NULL;
|
|
CalculGrandeurTravail(ptintmeca,def,TEMPS_tdt,dTP,ex_impli,ex_expli_tdt,ex_expli,NULL,NULL);
|
|
// calcul de : sigHH, d_sigHH
|
|
// on gère les exceptions éventuelles en mettant le bloc sous surveillance
|
|
try
|
|
{ Calcul_DsigmaHH_tdt (sigHH_t,DepsBB_,tab_ddl,*(ex.giB_t),*(ex.gijBB_t), *(ex.gijHH_t),
|
|
*(ex.giB_tdt),*(ex.d_giB_tdt),*(ex.giH_tdt),*(ex.d_giH_tdt),
|
|
epsBB_tdt,d_epsBB_tdt,delta_epsBB, *(ex.gijBB_tdt), *(ex.gijHH_tdt),
|
|
*(ex.d_gijBB_tdt), *(ex.d_gijHH_tdt),(*ex.jacobien_0), (*ex.jacobien_tdt),
|
|
*(ex.d_jacobien_tdt),sigHH, d_sigHH,energ,energ_t,module_compressibilite,module_cisaillement,ex);
|
|
}
|
|
catch (ErrSortieFinale)
|
|
// cas d'une direction voulue vers la sortie
|
|
// on relance l'interuption pour le niveau supérieur
|
|
{ ErrSortieFinale toto;
|
|
throw (toto);
|
|
}
|
|
catch ( ... ) // cas d'une erreur dans la recherche de la contrainte
|
|
{ throw ErrNonConvergence_loiDeComportement();
|
|
if (ParaGlob::NiveauImpression() >= 1)
|
|
{cout << "\n warning: exception generee par la loi de comportement ";
|
|
if (ParaGlob::NiveauImpression() >= 4) cout << "\n Loi_comp_abstraite::Cal_implicit(..";
|
|
};
|
|
};
|
|
jacobien = (*ex.jacobien_tdt);
|
|
d_jacobien_tdt = *(ex.d_jacobien_tdt);
|
|
// calcul éventuel des invariants de contraintes
|
|
CalculInvariants_contraintes(ptintmeca,*(ex.gijBB_tdt),*(ex.gijHH_tdt));
|
|
// en sortie il nous faut définir d_epsBB qui doit être égale à D*, donc pas forcément la dérivée
|
|
// de epsBB (par exemple dans le cas de la déformation logarithmique ou cumulée)
|
|
// variation de la déformation / au ddl
|
|
if (type_de_deformation != DEFORMATION_STANDART)
|
|
{ int d_epsBB_tdtTaille = d_epsBB_tdt.Taille();
|
|
for (int i=1; i<= d_epsBB_tdtTaille; i++)
|
|
*(d_epsBB_tdt(i)) = 0.5 * (*((*(ex.d_gijBB_tdt))(i)));
|
|
};
|
|
//------- affichage d'erreurs éventuelles ----
|
|
if (Permet_affichage() > 2)
|
|
{ // on regarde la taille des déformations
|
|
double maxsig = sigHH.MaxiComposante();
|
|
if (( maxsig > ConstMath::grand)
|
|
|| (!isfinite(maxsig)) || (isnan(maxsig))
|
|
)
|
|
if (!sortie_metrique)
|
|
{cout << "\n *** pb sur le calcul de la contrainte: le resultat est "
|
|
<< " soit infini soit un nan ";
|
|
Signature_pti_encours(cout);
|
|
def.Affiche();
|
|
};
|
|
|
|
};
|
|
#ifdef MISE_AU_POINT
|
|
if (Permet_affichage() > 5)
|
|
{cout << "\n Loi_comp_abstraite::Cal_implicit: sigHH_tdt ";
|
|
sigHH.Ecriture(cout);
|
|
cout << "\n jacobien= "<< jacobien << ", d_jacobien_tdt:";
|
|
d_jacobien_tdt.Affiche();
|
|
if (Permet_affichage() > 4)
|
|
for (int i = 1; i<= d_epsBB_tdt.Taille(); i++)
|
|
{ cout << "\n d_sigHH("<<i<<") ";
|
|
d_sigHH(i)->Ecriture(cout);
|
|
cout << "\n d_epsBB_tdt("<<i<<") ";
|
|
d_epsBB_tdt(i)->Ecriture(cout);
|
|
};
|
|
};
|
|
#endif
|
|
def_en_cours=NULL; // plus d'accès possible à la sortie
|
|
ptintmeca_en_cours = NULL; // plus d'accès possible à la sortie
|
|
temps_cpu_loi.Arret_du_comptage(); // cpu spécifique pti
|
|
temps_loi.Arret_du_comptage(); // cpu spécifique loi
|
|
////debug
|
|
//if (temps_cpu_loi.Temps_CPU_User() == 0)
|
|
// { cout << "\n Loi_comp_abstraite::Cal_implicit: sigHH_tdt ";
|
|
// cout << " *** étrange, le temps loi de comp est nul ! " << endl;
|
|
// };
|
|
//// fin debug
|
|
|
|
// retour
|
|
return ex; // retour de la métrique
|
|
};
|
|
// schema pour le flambage linéaire
|
|
void Loi_comp_abstraite::Cal_flamb_lin
|
|
(SaveResul * saveDon,Deformation & def,DdlElement & tab_ddl
|
|
,PtIntegMecaInterne & ptintmeca, Tableau <TenseurBB *>& d_epsBB_tdt
|
|
,double& jacobien,Vecteur& d_jacobien_tdt,Tableau <TenseurHH *>& d_sigHH,const ParaAlgoControle &
|
|
,CompThermoPhysiqueAbstraite::SaveResul * saveTP,CompThermoPhysiqueAbstraite* loiTP
|
|
,bool dilat,EnergieMeca & energ,const EnergieMeca & energ_t,bool premier_calcul
|
|
)
|
|
{
|
|
Temps_CPU_HZpp& temps_cpu_loi = ptintmeca.Tps_cpu_loi_comp();
|
|
temps_cpu_loi.Mise_en_route_du_comptage(); // spécifique pti
|
|
temps_loi.Mise_en_route_du_comptage(); // spécifique loi
|
|
// passage des infos specifiques aux classes derivantes
|
|
saveResul = saveDon;
|
|
def_en_cours=&def;
|
|
// récup des contraintes
|
|
TenseurHH & sigHH = *(ptintmeca.SigHH()); // ici _tdt est la grandeur finale
|
|
TenseurHH & sigHH_t = *(ptintmeca.SigHH_t()); // ici _tdt est la grandeur finale
|
|
TenseurBB & epsBB_tdt = *(ptintmeca.EpsBB());
|
|
TenseurBB & DepsBB_ = *(ptintmeca.DepsBB());
|
|
TenseurBB & delta_epsBB = *(ptintmeca.DeltaEpsBB());
|
|
double& module_compressibilite = ptintmeca.ModuleCompressibilite();
|
|
double& module_cisaillement = ptintmeca.ModuleCisaillement();
|
|
Tableau <double>& def_equi = ptintmeca.Deformation_equi();
|
|
const Tableau <double>& def_equi_t = ptintmeca.Deformation_equi_t_const();
|
|
dilatation=dilat;
|
|
ptintmeca_en_cours = &ptintmeca; // pour les méthodes internes
|
|
|
|
// calcul des éléments de métrique
|
|
Temps_CPU_HZpp& temps_cpu_metrique = ptintmeca.TpsMetrique();
|
|
temps_cpu_metrique.Mise_en_route_du_comptage(); // cpu
|
|
const Met_abstraite::flambe_lin& ex = def.Cal_flambe_lin
|
|
(def_equi_t,epsBB_tdt,d_epsBB_tdt,def_equi,DepsBB_,delta_epsBB,premier_calcul);
|
|
// on récupère les positions des points
|
|
if (premier_calcul)
|
|
{ptintmeca.M_0() = def.Position_0();
|
|
ptintmeca.M_t() = def.Position_t();
|
|
};
|
|
ptintmeca.M_tdt() = def.Position_tdt();
|
|
temps_cpu_metrique.Arret_du_comptage(); // cpu
|
|
// dans le cas d'une loi thermo dépendante, calcul de la température
|
|
if ((thermo_dependant) || dilatation)
|
|
{temperature_0 = def.DonneeInterpoleeScalaire(TEMP,TEMPS_0);
|
|
temperature_t = def.DonneeInterpoleeScalaire(TEMP,TEMPS_t);
|
|
temperature_tdt = def.DonneeInterpoleeScalaire(TEMP,TEMPS_tdt);
|
|
temperature=&temperature_tdt;
|
|
};
|
|
// dans le cas ou l'on tiens compte de la dilatation on modifie les différents tenseurs de déformation
|
|
ThermoDonnee dTP; // init à 0 par défaut
|
|
if (dilatation)
|
|
{ // attention ici on utilise la contrainte du temps précédent, il pourrait y avoir des oscillations
|
|
// vu que sigma suivant dépend de epsméca et que epsmeca dépend de sigma !!!
|
|
// double P = -(sigHH_t * (*(ex.gijBB_tdt))).Trace()/Abs(sigHH_t.Dimension()); // calcul de la pression
|
|
// on utilise la valeur à tdt, qui est donc celle calculée à l'itération précédente en implicite
|
|
// en espérant que cela veuille dire quelque chose ici !!
|
|
double P = -(sigHH * (*(ex.gijBB_tdt))).Trace()/Abs(sigHH.Dimension()); // calcul de la pression
|
|
// et celle du pas précédent
|
|
double P_t = -(sigHH_t * (*(ex.gijBB_t))).Trace()/Abs(sigHH_t.Dimension()); // calcul de la pression à t
|
|
loiTP->Cal_donnees_thermiques(P_t,saveTP,def,P,TEMPS_tdt,dTP);
|
|
// modification de la déformation mécanique et calcul de la déformation thermique
|
|
// a- dimensionnement des tenseurs intermédiaires qui pour l'instant ne servent qu'ici
|
|
int dim_tens = epsBB_tdt.Dimension();
|
|
// -- cas de la déformation
|
|
if (epsBB_totale == NULL) { epsBB_totale = NevezTenseurBB(dim_tens);}
|
|
else if (epsBB_totale->Dimension() != dim_tens) { delete epsBB_totale;epsBB_totale = NevezTenseurBB(dim_tens);};
|
|
*epsBB_totale = epsBB_tdt;
|
|
if (epsBB_therm == NULL) { epsBB_therm = NevezTenseurBB(dim_tens);}
|
|
else if (epsBB_therm->Dimension() != dim_tens) { delete epsBB_therm;epsBB_therm = NevezTenseurBB(dim_tens);};
|
|
// -- cas de la vitesse de déformation
|
|
if (DepsBB_totale == NULL) { DepsBB_totale = NevezTenseurBB(dim_tens);}
|
|
else if (DepsBB_totale->Dimension() != dim_tens) { delete DepsBB_totale;DepsBB_totale = NevezTenseurBB(dim_tens);};
|
|
*DepsBB_totale = DepsBB_;
|
|
if (DepsBB_therm == NULL) { DepsBB_therm = NevezTenseurBB(dim_tens);}
|
|
else if (DepsBB_therm->Dimension() != dim_tens) { delete DepsBB_therm;DepsBB_totale = NevezTenseurBB(dim_tens);};
|
|
// -- calcul du partage entre thermique et mécanique
|
|
bool avec_repercution_sur_def_meca = true;
|
|
def.DeformationThermoMecanique(temperature_0,*(ex.gijBB_tdt),dTP,*epsBB_totale
|
|
,*epsBB_therm,temperature_tdt,epsBB_tdt,temperature_tdt
|
|
,*DepsBB_totale,*DepsBB_therm,DepsBB_,true,avec_repercution_sur_def_meca);
|
|
};
|
|
if ((thermo_dependant) || dilatation) // répercussion éventuelle du changement de température dans les classes dérivées
|
|
{ RepercuteChangeTemperature(TEMPS_tdt); };
|
|
// calcul éventuel des invariants liés à la cinématique
|
|
CalculInvariants_cinematique(ptintmeca,*(ex.gijBB_t),*(ex.gijHH_t));
|
|
// demande dans les classes dérivées du calcul de grandeurs spécifiques si besoin est
|
|
const Met_abstraite::Impli* ex_impli = &ex;
|
|
const Met_abstraite::Expli_t_tdt* ex_expli_tdt = NULL;
|
|
const Met_abstraite::Umat_cont* ex_expli = NULL;
|
|
CalculGrandeurTravail(ptintmeca,def,TEMPS_tdt,dTP,ex_impli,ex_expli_tdt,ex_expli,NULL,NULL);
|
|
// calcul de : sigHH, d_sigHH
|
|
// on gère les exceptions éventuelles en mettant le bloc sous surveillance
|
|
try
|
|
{ Calcul_DsigmaHH_tdt (sigHH_t,DepsBB_,tab_ddl,*(ex.giB_t),*(ex.gijBB_t), *(ex.gijHH_t),*(ex.giB_tdt)
|
|
,*(ex.d_giB_tdt),*(ex.giH_tdt),*(ex.d_giH_tdt)
|
|
,epsBB_tdt,d_epsBB_tdt,delta_epsBB, *(ex.gijBB_tdt), *(ex.gijHH_tdt)
|
|
,*(ex.d_gijBB_tdt), *(ex.d_gijHH_tdt),(*ex.jacobien_0), (*ex.jacobien_tdt)
|
|
,*(ex.d_jacobien_tdt),sigHH, d_sigHH,energ,energ_t,module_compressibilite,module_cisaillement,
|
|
ex);
|
|
}
|
|
catch (ErrSortieFinale)
|
|
// cas d'une direction voulue vers la sortie
|
|
// on relance l'interuption pour le niveau supérieur
|
|
{ ErrSortieFinale toto;
|
|
throw (toto);
|
|
}
|
|
catch ( ... ) // cas d'une erreur dans la recherche de la contrainte
|
|
{ throw ErrNonConvergence_loiDeComportement();
|
|
if (ParaGlob::NiveauImpression() >= 1)
|
|
cout << "\n warning: exception generee par la loi de comportement ";
|
|
if (ParaGlob::NiveauImpression() >= 4) cout << "\n Loi_comp_abstraite::Cal_flamb_lin(..";
|
|
};
|
|
jacobien = (*ex.jacobien_tdt);
|
|
d_jacobien_tdt = *(ex.d_jacobien_tdt);
|
|
// calcul éventuel des invariants de contraintes
|
|
CalculInvariants_contraintes(ptintmeca,*(ex.gijBB_tdt),*(ex.gijHH_tdt));
|
|
// en sortie il nous faut définir d_epsBB qui doit être égale à D*, donc pas forcément la dérivée
|
|
// de epsBB (par exemple dans le cas de la déformation logarithmique ou cumulée)
|
|
// variation de la déformation / au ddl
|
|
if (type_de_deformation != DEFORMATION_STANDART)
|
|
{ int d_epsBB_tdtTaille = d_epsBB_tdt.Taille();
|
|
for (int i=1; i<= d_epsBB_tdtTaille; i++)
|
|
*(d_epsBB_tdt(i)) = 0.5 * (*((*(ex.d_gijBB_tdt))(i)));
|
|
};
|
|
def_en_cours=NULL; // plus d'accès possible à la sortie
|
|
ptintmeca_en_cours = NULL; // plus d'accès possible à la sortie
|
|
temps_cpu_loi.Arret_du_comptage(); // cpu spécifique pti
|
|
temps_loi.Arret_du_comptage(); // cpu spécifique loi
|
|
// retour
|
|
};
|
|
|
|
// schema pour le calcul de la loi de comportement dans le cas de l'umat
|
|
void Loi_comp_abstraite::ComportementUmat
|
|
(Loi_comp_abstraite::SaveResul * saveDon
|
|
,Deformation & def,PtIntegMecaInterne& ptintmeca,ParaAlgoControle & para
|
|
,CompThermoPhysiqueAbstraite::SaveResul * saveTP,CompThermoPhysiqueAbstraite* loiTP
|
|
,bool dilat,UmatAbaqus& umatAbaqusqus,bool premier_calcul)
|
|
{
|
|
Temps_CPU_HZpp& temps_cpu_loi = ptintmeca.Tps_cpu_loi_comp();
|
|
temps_cpu_loi.Mise_en_route_du_comptage(); // spécifique pti
|
|
temps_loi.Mise_en_route_du_comptage(); // spécifique loi
|
|
// passage des infos specifiques aux classes derivantes
|
|
saveResul = saveDon;
|
|
dilatation=dilat;
|
|
def_en_cours=&def;
|
|
ptintmeca_en_cours = &ptintmeca; // pour les méthodes internes
|
|
|
|
// on calcul les éléments de la métrique dans le cas particulier de l'umat d'où d'une métrique
|
|
// Met_ElemPoint et d'une déformation particulière Def_Umat
|
|
Def_Umat& defUmat = *((Def_Umat*) &def); // récup
|
|
// on regarde si c'est le premier incrément ou pas (d'où le calcul du premier pas)
|
|
// bool premier_calcul=false;
|
|
// if (umatAbaqusqus.nb_increment <= 1) premier_calcul = true;
|
|
Temps_CPU_HZpp& temps_cpu_metrique = ptintmeca.TpsMetrique();
|
|
temps_cpu_metrique.Mise_en_route_du_comptage(); // cpu
|
|
const Met_abstraite::Umat_cont& ex= defUmat.Cal_defUmat(premier_calcul);
|
|
// on récupère les positions des points
|
|
if (premier_calcul)
|
|
{ptintmeca.M_0() = def.Position_0();
|
|
ptintmeca.M_t() = def.Position_t();
|
|
};
|
|
ptintmeca.M_tdt() = def.Position_tdt();
|
|
umatAbaqusqus.coor_pt = ptintmeca.M_tdt();// on met à jour les coordonnées absolues du pti temps_cpu_metrique.Arret_du_comptage(); // cpu
|
|
// -- modification du pas de temps: on part du principe que le pas de temps est géré par le programme appelant donc ici on ne fait que répercuter
|
|
// -- le pas de temps et le temps courant au niveau des paramètres globaux du calcul, qui normalement ne sont (et ne doivent être)
|
|
// -- utilisées que pour la loi de comportement Umat. Les autres cas ne sont pas prévus
|
|
para.Modif_temps(umatAbaqusqus.temps_tdt,umatAbaqusqus.delta_t);
|
|
// // modif le 21 avril 2016 -> on passe les infos via des paramètres de passage
|
|
// // double deltat = umatAbaqusqus.delta_t;
|
|
// // VariablesTemps tempo_umat(para.Variables_de_temps());
|
|
// // ici on accède directement car c'est loi_comp_abstraite est friend de Variables Temps
|
|
// tempo_umat.temps = umatAbaqusqus.temps_tdt;
|
|
// tempo_umat.deltat = umatAbaqusqus.delta_t;
|
|
|
|
|
|
// dans le cas d'une loi thermo dépendante, calcul de la température
|
|
if ((thermo_dependant) || dilatation)
|
|
{temperature_0 = 0.; // a priori pour l'instant
|
|
temperature_t = umatAbaqusqus.temper_t;
|
|
temperature_tdt = umatAbaqusqus.temper_t+umatAbaqusqus.delta_temper;
|
|
temperature=&temperature_tdt;
|
|
};
|
|
#ifdef MISE_AU_POINT
|
|
if ( Permet_affichage() > 5)
|
|
{cout << "\n temperature_0= "<< temperature_0
|
|
<< " temperature_t= "<< temperature_t
|
|
<< " temperature= "<< temperature
|
|
<< "\n thermo_dependant= "<<thermo_dependant
|
|
<< " dilatation= "<< dilatation
|
|
<< flush;
|
|
};
|
|
#endif
|
|
// -- cas de la vitesse de déformation à la umat
|
|
// construction du tenseur vitesse de déformation, constant sur le pas de temps
|
|
// = delta epsilonBB /delta t
|
|
if (DepsBB_umat == NULL) // cas du premier passage, on cré le tenseur
|
|
{ DepsBB_umat = NevezTenseurBB(*(umatAbaqusqus.delta_eps_meca));}
|
|
else if (DepsBB_umat->Dimension() != (umatAbaqusqus.delta_eps_meca)->Dimension()) // tenseur inadapté, on change
|
|
{ delete DepsBB_umat;DepsBB_umat = NevezTenseurBB(*(umatAbaqusqus.delta_eps_meca));}
|
|
else // cas courant on récupère la valeur de delta_epsilon_BB
|
|
{ *DepsBB_umat = *(umatAbaqusqus.delta_eps_meca); };
|
|
// puis on divise par l'incrément de temsp
|
|
if (Abs(umatAbaqusqus.delta_t) >= ConstMath::trespetit)
|
|
{(*DepsBB_umat) /= umatAbaqusqus.delta_t;}
|
|
else {DepsBB_umat->Inita(0.);}; // si trop petit on met à 0
|
|
|
|
ThermoDonnee dTP; // init à 0 par défaut
|
|
if (dilatation)
|
|
{ // attention ici on utilise la contrainte du temps précédent, car a priori on ne dispose pas de la nouvelle valeur
|
|
// il pourrait y avoir des oscillations
|
|
// dans le cas de l'umat, le tenseur initial sigma est en orthonormée
|
|
double P=0.;
|
|
for (int i=1;i<=umatAbaqusqus.dim_tens;i++) P += (*umatAbaqusqus.t_sigma)(i,i);
|
|
P /= umatAbaqusqus.dim_tens; // pression
|
|
loiTP->Cal_donnees_thermiques(P,saveTP,def,P,TEMPS_tdt,dTP);
|
|
// Dans le cas de la procédure Umat, la déformation récupérée est directement la déformation mécanique
|
|
// l'influence de la dilatation thermique s'effectue éventullement au sein de la loi de comportement
|
|
// comme par exemple Hysteresis_bulk, quand on utilise pas directement les deformations méca
|
|
// a- dimensionnement des tenseurs intermédiaires qui pour l'instant ne servent qu'ici
|
|
// epsBB_totale et DepsBB_totale ne servent à rien en fait ... l'objectif est uniquement de satifaire
|
|
// les variables de passages dans DeformationThermoMecanique, car comme avec_repercution_sur_def_meca = false
|
|
// on ne change pas les tenseurs de déformation et de vitesse de déformation
|
|
// par contre : epsBB_therm et DepsBB_therm sont calculées dans DeformationThermoMecanique
|
|
int dim_tens = 3; // a priori on est en dimension 3
|
|
// -- cas de la déformation
|
|
if (epsBB_totale == NULL) { epsBB_totale = NevezTenseurBB(dim_tens);}
|
|
else if (epsBB_totale->Dimension() != dim_tens) { delete epsBB_totale;epsBB_totale = NevezTenseurBB(dim_tens);};
|
|
if (epsBB_therm == NULL) { epsBB_therm = NevezTenseurBB(dim_tens);}
|
|
else if (epsBB_therm->Dimension() != dim_tens) { delete epsBB_therm;epsBB_therm = NevezTenseurBB(dim_tens);};
|
|
// -- cas de la vitesse de déformation
|
|
if (DepsBB_totale == NULL) { DepsBB_totale = NevezTenseurBB(dim_tens);}
|
|
else if (DepsBB_totale->Dimension() != dim_tens) { delete DepsBB_totale;DepsBB_totale = NevezTenseurBB(dim_tens);};
|
|
if (DepsBB_therm == NULL) { DepsBB_therm = NevezTenseurBB(dim_tens);}
|
|
else if (DepsBB_therm->Dimension() != dim_tens) { delete DepsBB_therm;DepsBB_totale = NevezTenseurBB(dim_tens);};
|
|
// -- calcul du partage entre thermique et mécanique
|
|
bool avec_repercution_sur_def_meca = false;
|
|
def.DeformationThermoMecanique(temperature_0,*(ex.gijBB_tdt),dTP,*epsBB_totale
|
|
,*epsBB_therm,temperature_tdt,*(umatAbaqusqus.eps_meca),temperature_t
|
|
,*DepsBB_totale,*DepsBB_therm,*DepsBB_umat,true,avec_repercution_sur_def_meca);
|
|
};
|
|
// cas des énergie méca
|
|
// tout d'abord celles précédentes
|
|
EnergieMeca ener_t(umatAbaqusqus.energie_elastique,umatAbaqusqus.dissipation_plastique
|
|
,umatAbaqusqus.dissipation_visqueuse);
|
|
EnergieMeca ener; // la sortie initialisée à 0
|
|
// transfert de l'Umat vers les pt d'integ avant le calcul de la contrainte donc à t
|
|
umatAbaqusqus.Transfert_Umat_ptInteg_t(ptintmeca);
|
|
*(ptintmeca.DepsBB())=*DepsBB_umat; // stockage de vitesse de déformation
|
|
// calcul des def équivalentes
|
|
// - récup des infos
|
|
TenseurBB & epsBB_tdt = *(ptintmeca.EpsBB());
|
|
TenseurBB & DepsBB_ = *(ptintmeca.DepsBB());
|
|
TenseurBB & delta_epsBB = *(ptintmeca.DeltaEpsBB());
|
|
Tableau <double>& def_equi = ptintmeca.Deformation_equi();
|
|
const Tableau <double>& def_equi_t = ptintmeca.Deformation_equi_t_const();
|
|
// - calcul
|
|
defUmat.CalDefEqui(def_equi_t,epsBB_tdt,def_equi,DepsBB_,delta_epsBB,ex,premier_calcul);
|
|
|
|
if ((thermo_dependant) || dilatation) // répercussion éventuelle du changement de température dans les classes dérivées
|
|
{ RepercuteChangeTemperature(TEMPS_tdt); };
|
|
// calcul éventuel des invariants liés à la cinématique
|
|
CalculInvariants_cinematique(ptintmeca,*(ex.gijBB_t),*(ex.gijHH_t));
|
|
// calcul éventuel préalable avant le calcul de la contrainte
|
|
const Met_abstraite::Impli* ex_impli = NULL;
|
|
const Met_abstraite::Expli_t_tdt* ex_expli_tdt = NULL;
|
|
const Met_abstraite::Umat_cont* ex_expli = &ex;
|
|
CalculGrandeurTravail(ptintmeca,defUmat,TEMPS_tdt,dTP,ex_impli,ex_expli_tdt,ex_expli,NULL,NULL);
|
|
|
|
// affichage de certaines données de def d'entrée du calcul Calcul_dsigma_deps
|
|
// car elles sont différentes (car calculées) en fonction des entrées
|
|
#ifdef MISE_AU_POINT
|
|
if (((ParaGlob::NiveauImpression() > 8) && (Permet_affichage() == 0))
|
|
|| (Permet_affichage() > 4)
|
|
)
|
|
{ cout << "\n affichage des def avant appel de Calcul_dsigma_deps \n ";
|
|
int dim = ParaGlob::Dimension();
|
|
// def en orthonormee
|
|
TenseurBB* epsBB_inter= (NevezTenseurBB(dim)) ;
|
|
(umatAbaqusqus.eps_meca)->BaseAbsolue(*epsBB_inter,*(ex.giH_tdt));
|
|
cout << "\n epsBB meca d'entree =en orthonormee ";epsBB_inter->Ecriture(cout);
|
|
delete epsBB_inter;
|
|
// Deps
|
|
TenseurBB* DepsBB_inter= (NevezTenseurBB(dim)) ;
|
|
DepsBB_umat->BaseAbsolue(*DepsBB_inter,*(ex.giH_tdt));
|
|
cout << "\n DepsBB meca d'entree =en orthonormee "; DepsBB_inter->Ecriture(cout);
|
|
delete DepsBB_inter;
|
|
// Delta eps
|
|
TenseurBB* delta_epsBB_inter= (NevezTenseurBB(dim)) ;
|
|
(umatAbaqusqus.delta_eps_meca)->BaseAbsolue(*delta_epsBB_inter,*(ex.giH_tdt));
|
|
cout << "\n delta eps meca d'entree =en orthonormee "; delta_epsBB_inter->Ecriture(cout);
|
|
delete delta_epsBB_inter;
|
|
cout << endl;
|
|
};
|
|
#endif
|
|
|
|
// calcul de : sigHH, d_sigHH
|
|
bool en_base_orthonormee=true; // ici les tenseurs sont en orthonormee a priori
|
|
// on gère les exceptions éventuelles en mettant le bloc sous surveillance
|
|
try
|
|
{ Calcul_dsigma_deps(en_base_orthonormee, *(umatAbaqusqus.t_sigma),*DepsBB_umat
|
|
,*(umatAbaqusqus.eps_meca),*(umatAbaqusqus.delta_eps_meca)
|
|
,(*ex.jacobien_0),(*ex.jacobien_tdt)
|
|
,*(umatAbaqusqus.t_sigma),*(umatAbaqusqus.d_sigma_deps)
|
|
,ener,ener_t,ptintmeca.ModuleCompressibilite(),ptintmeca.ModuleCisaillement(),ex
|
|
) ;
|
|
}
|
|
catch (ErrSortieFinale)
|
|
// cas d'une direction voulue vers la sortie
|
|
// on relance l'interuption pour le niveau supérieur
|
|
{ ErrSortieFinale toto;
|
|
throw (toto);
|
|
}
|
|
catch ( ... ) // cas d'une erreur dans la recherche de la contrainte
|
|
{ throw ErrNonConvergence_loiDeComportement();
|
|
if (ParaGlob::NiveauImpression() >= 1)
|
|
cout << "\n warning: exception generee par la loi de comportement ";
|
|
if (ParaGlob::NiveauImpression() >= 4) cout << "\n Loi_comp_abstraite::ComportementUmat(..";
|
|
};
|
|
umatAbaqusqus.energie_elastique = ener.EnergieElastique();
|
|
umatAbaqusqus.dissipation_plastique = ener.DissipationPlastique();
|
|
umatAbaqusqus.dissipation_visqueuse= ener.DissipationVisqueuse();
|
|
// dans le cas où il s'agit d'une loi de contrainte plane, on met à jour les normales finales
|
|
// ce qui permettra de transmettre la variation d'épaisseur
|
|
if ((Comp_3D_CP_DP_1D(this->Id_comport()) == COMP_CONTRAINTES_PLANES)
|
|
&& (ParaGlob::Dimension() == 3))
|
|
{ umatAbaqusqus.N_tdt(3) = HsurH0(saveDon);
|
|
};
|
|
|
|
// transfert de l'Umat vers les pt d'integ
|
|
// umatAbaqusqus.Transfert_Umat_ptInteg_t(ptintmeca); // correction erreur le 7/sept/ 2013
|
|
umatAbaqusqus.Transfert_Umat_ptInteg_tdt(ptintmeca); // correction erreur le 7/sept/ 2013
|
|
// calcul éventuel des invariants de contraintes
|
|
CalculInvariants_contraintes(ptintmeca,*(ex.gijBB_tdt),*(ex.gijHH_tdt));
|
|
def_en_cours=NULL; // plus d'accès possible à la sortie
|
|
ptintmeca_en_cours = NULL; // plus d'accès possible à la sortie
|
|
temps_cpu_loi.Arret_du_comptage(); // cpu spécifique pti
|
|
temps_loi.Arret_du_comptage(); // cpu spécifique loi
|
|
};
|
|
|
|
// calcul d'un module d'young équivalent à la loi, ceci pour un
|
|
// chargement nul
|
|
double Loi_comp_abstraite::Module_young_equivalent(Enum_dure ,const Deformation & ,SaveResul * )
|
|
{ cout << "\n erreur , aucun module d'young equivalent n'est defini pour cette loi ";
|
|
this->Affiche();
|
|
Sortie(1);
|
|
return 0.; // pour éviter le warning à la compil
|
|
};
|
|
// récupération d'un module de compressibilité équivalent à la loi pour un chargement nul
|
|
// il s'agit ici de la relation -pression = sigma_trace/3. = module de compressibilité * I_eps
|
|
double Loi_comp_abstraite::Module_compressibilite_equivalent(Enum_dure ,const Deformation & ,SaveResul * )
|
|
{ cout << "\n erreur , aucun module de compressibilite equivalent n'est defini pour cette loi ";
|
|
this->Affiche();
|
|
Sortie(1);
|
|
return 0.; // pour éviter le warning à la compil
|
|
};
|
|
|
|
// récupération de la dernière déformation d'épaisseur calculée: cette déformaion n'est utile que pour des lois en contraintes planes ou doublement planes
|
|
// - pour les lois 3D : retour d'un nombre très grand, indiquant que cette fonction est invalide
|
|
// - pour les lois 2D def planes: retour de 0
|
|
// les infos nécessaires à la récupération de la def, sont stockées dans saveResul
|
|
// qui est le conteneur spécifique au point où a été calculé la loi
|
|
double Loi_comp_abstraite::Eps33BH(SaveResul * saveResul) const
|
|
{ cout << "\n erreur , la methode Eps33BH() n'est defini pour cette loi ";
|
|
this->Affiche();
|
|
Sortie(1);
|
|
return 0.; // pour éviter le warning à la compil
|
|
};
|
|
|
|
|
|
// récupération de la dernière déformation de largeur calculée: cette déformaion n'est utile que pour des lois en contraintes doublement planes
|
|
// - pour les lois 3D et 2D : retour d'un nombre très grand, indiquant que cette fonction est invalide
|
|
// les infos nécessaires à la récupération de la def, sont stockées dans saveResul
|
|
// qui est le conteneur spécifique au point où a été calculé la loi
|
|
double Loi_comp_abstraite::Eps22BH(SaveResul * saveResul) const
|
|
{ cout << "\n erreur , la methode Eps22BH() n'est defini pour cette loi ";
|
|
this->Affiche();
|
|
Sortie(1);
|
|
return 0.; // pour éviter le warning à la compil
|
|
};
|
|
|
|
// récupération de la variation relative d'épaisseur calculée: h/h0
|
|
// et de sa variation par rapport aux ddls la concernant: d_hsurh0
|
|
// cette variation n'est utile que pour des lois en contraintes planes
|
|
// - pour les lois 3D : retour d'un nombre très grand, indiquant que cette fonction est invalide
|
|
// - pour les lois 2D def planes: retour de 0
|
|
// les infos nécessaires à la récupération , sont stockées dans saveResul
|
|
// qui est le conteneur spécifique au point où a été calculé la loi
|
|
double Loi_comp_abstraite::d_HsurH0(SaveResul * saveResul,Vecteur & d_hsurh0) const
|
|
{ cout << "\n erreur , la methode d_HsurH0() n'est defini pour cette loi ";
|
|
this->Affiche();
|
|
Sortie(1);
|
|
return 0.; // pour éviter le warning à la compil
|
|
};
|
|
|
|
// récupération de la variation relative de largeur calculée: b/b0
|
|
// cette variation n'est utile que pour des lois en contraintes planes double
|
|
// - pour les lois 3D et 2D : retour d'un nombre très grand, indiquant que cette fonction est invalide
|
|
// les infos nécessaires à la récupération , sont stockées dans saveResul
|
|
// qui est le conteneur spécifique au point où a été calculé la loi
|
|
double Loi_comp_abstraite::BsurB0(SaveResul * saveResul) const
|
|
{ cout << "\n erreur , la methode BsurB0() n'est defini pour cette loi ";
|
|
this->Affiche();
|
|
Sortie(1);
|
|
return 0.; // pour éviter le warning à la compil
|
|
};
|
|
|
|
// récupération de la variation relative de largeur calculée: b/b0
|
|
// et de sa variation par rapport aux ddls la concernant: d_bsurb0
|
|
// cette variation n'est utile que pour des lois en contraintes planes
|
|
// - pour les lois 3D et 2D : retour d'un nombre très grand, indiquant que cette fonction est invalide
|
|
// les infos nécessaires à la récupération , sont stockées dans saveResul
|
|
// qui est le conteneur spécifique au point où a été calculé la loi
|
|
double Loi_comp_abstraite::d_BsurB0(SaveResul * saveResul,Vecteur & d_bsurb0) const
|
|
{ cout << "\n erreur , la methode d_BsurB0() n'est defini pour cette loi ";
|
|
this->Affiche();
|
|
Sortie(1);
|
|
return 0.; // pour éviter le warning à la compil
|
|
};
|
|
|
|
|
|
// mise à jour des températures d'une manière unilatérale: sert par exemple pour
|
|
// le calcul du module d'young équivalent, quand il est calculé en dehors du calcul des contraintes
|
|
void Loi_comp_abstraite::Mise_a_jour_temperature(Enum_dure temps,Deformation & def)
|
|
{
|
|
if (thermo_dependant)
|
|
{switch (temps)
|
|
{ case TEMPS_0:
|
|
temperature_0 = def.DonneeInterpoleeScalaire(TEMP,TEMPS_0);
|
|
temperature = &temperature_0;
|
|
break;
|
|
case TEMPS_t:
|
|
temperature_t = def.DonneeInterpoleeScalaire(TEMP,TEMPS_t);
|
|
temperature = &temperature_t;
|
|
break;
|
|
case TEMPS_tdt:
|
|
temperature_tdt = def.DonneeInterpoleeScalaire(TEMP,TEMPS_tdt);
|
|
temperature = &temperature_tdt;
|
|
break;
|
|
default :
|
|
cout << "\n cas du temps non implante temps= " << Nom_dure(temps)
|
|
<< "\n Loi_comp_abstraite::Mise_a_jour_temperature(Enum_dure temps...";
|
|
Sortie(1);
|
|
};
|
|
// puis on répercute la température
|
|
RepercuteChangeTemperature(temps);
|
|
};
|
|
|
|
};
|
|
|
|
// lecture éventuelle du type de déformation et du niveau de commentaire
|
|
void Loi_comp_abstraite::Lecture_type_deformation_et_niveau_commentaire
|
|
(UtilLecture& entreePrinc,LesFonctions_nD& lesFonctionsnD
|
|
,bool avec_passage_nouvelle_donnee)
|
|
{
|
|
string nom_class_methode("Loi_comp_abstraite::Lecture_type_deformation_et_niveau_commentaire(..");
|
|
// recherche du mot clé éventuel indiquant le type de déformation
|
|
if (avec_passage_nouvelle_donnee)
|
|
entreePrinc.NouvelleDonnee();
|
|
// on note ce qu'il faut lire
|
|
int a_lire_type_deformation = 0;
|
|
if (strstr(entreePrinc.tablcar,"type_de_deformation")!= NULL)
|
|
a_lire_type_deformation = 1;
|
|
int a_lire_permet_affichage = 0;
|
|
if (strstr(entreePrinc.tablcar,"permet_affichage_")!= NULL)
|
|
a_lire_permet_affichage = 1;
|
|
// on initialise par défaut: la déformation standart
|
|
type_de_deformation = DEFORMATION_STANDART;
|
|
// le niveau de commentaire local
|
|
// on ne l'initialise pas car il peut déjà avoir une valeur
|
|
// via une lecture de paramètres particuliers permet_affichage = 0;
|
|
|
|
if ( a_lire_type_deformation || a_lire_permet_affichage)
|
|
{while ( a_lire_type_deformation || a_lire_permet_affichage)
|
|
{ // on lit le mot clé
|
|
string nom;
|
|
*(entreePrinc.entree) >> nom;
|
|
if (nom == "type_de_deformation")
|
|
{ *(entreePrinc.entree) >> nom ;
|
|
type_de_deformation=Id_nom_type_deformation(nom.c_str());
|
|
a_lire_type_deformation = 0;
|
|
entreePrinc.NouvelleDonnee();
|
|
if (strstr(entreePrinc.tablcar,"permet_affichage_")!= NULL)
|
|
a_lire_permet_affichage = 1;
|
|
}
|
|
else if (nom == "permet_affichage_")
|
|
{Loi_comp_abstraite::Lecture_permet_affichage(&entreePrinc,lesFonctionsnD);
|
|
a_lire_permet_affichage = 0;
|
|
entreePrinc.NouvelleDonnee();
|
|
if (strstr(entreePrinc.tablcar,"type_de_deformation")!= NULL)
|
|
a_lire_type_deformation = 1;
|
|
}
|
|
else
|
|
{cout << "\n erreur*** : on a lue " << nom
|
|
<< " et on attendait un des deux mots clefs suivant: "
|
|
<< " type_de_deformation ou permet_affichage_ "
|
|
<< "\n Loi_comp_abstraite::Lecture_type_deformation_et_niveau_commentaire(.. "
|
|
<< endl;
|
|
Sortie(1);
|
|
};
|
|
};
|
|
};
|
|
|
|
};
|
|
|
|
// affichage des données de la classe comp_abstraite
|
|
void Loi_comp_abstraite::Affiche_don_classe_abstraite() const
|
|
{ cout << "\n type_de_deformation: " << Nom_type_deformation(type_de_deformation);
|
|
{cout << "\n list_grandeur_particuliere_dispo_localement:taille= "
|
|
<< listdeTouslesQuelc_dispo_localement.size()<<" ";
|
|
list <EnumTypeQuelconque >::const_iterator il,ilfin=listdeTouslesQuelc_dispo_localement.end();
|
|
for (il=listdeTouslesQuelc_dispo_localement.begin();il != ilfin;il++)
|
|
cout << NomTypeQuelconque(*il) << " ";
|
|
};
|
|
{cout << "\n list_grandeur_particuliere_demandee_localement:taille= "
|
|
<< listQuelc_mis_en_acces_localement.size()<<" ";
|
|
list <EnumTypeQuelconque >::const_iterator il,ilfin=listQuelc_mis_en_acces_localement.end();
|
|
for (il=listQuelc_mis_en_acces_localement.begin();il != ilfin;il++)
|
|
cout << NomTypeQuelconque(*il) << " ";
|
|
};
|
|
|
|
cout << endl;
|
|
};
|
|
|
|
// affichage et definition interactive des commandes particulières à la classe loi_comp_abstraite
|
|
void Loi_comp_abstraite::Info_commande_don_LoisDeComp(UtilLecture& entreePrinc) const
|
|
{ ofstream & sort = *(entreePrinc.Commande_pointInfo()); // pour simplifier
|
|
cout << "\n definition standart de la deformation (rep o (defaut) ou n) ? ";
|
|
string rep = "_";
|
|
// procédure de lecture avec prise en charge d'un retour chariot
|
|
rep = lect_return_defaut(true,"o");
|
|
|
|
if ((Minuscules(rep) != "f")&&(Minuscules(rep) != "0")&&(Minuscules(rep) != "o"))
|
|
{rep = "_";
|
|
while ((Minuscules(rep) != "f")&&(Minuscules(rep) != "0")&&(Minuscules(rep) != "o")
|
|
&&(Minuscules(rep) != "1")&&(Minuscules(rep) != "2"))
|
|
{try
|
|
{
|
|
cout << "\n -- definition du type de mesure de deformation : --- "
|
|
<< "\n (0 ou f) (fin) "
|
|
<< "\n (1) Almansi (defaut) "
|
|
<< "\n (2) Logarithmique (experimental) "
|
|
<< "\n ";
|
|
// procédure de lecture avec prise en charge d'un retour chariot
|
|
rep = lect_return_defaut(true,"1");
|
|
if ((Minuscules(rep) != "f")&&(Minuscules(rep) != "0")&&(Minuscules(rep) != "o")
|
|
&&(Minuscules(rep) != "1"))
|
|
{ if (Minuscules(rep) == "2")
|
|
{cout << "\n choix de la deformation Logarithmique ";
|
|
sort << "\n# -- definition du type de deformation (par defaut: DEFORMATION_STANDART) -- "
|
|
<< "\n type_de_deformation DEFORMATION_LOGARITHMIQUE ";
|
|
}
|
|
else { cout << "\n Erreur on attendait un entier entre 0 et 2 !!, "
|
|
<< "\n redonnez une bonne valeur"
|
|
<< "\n ou taper f ou 0 pour stoper la definition de la deformation ";
|
|
};
|
|
}
|
|
}
|
|
catch (ErrSortieFinale)
|
|
// cas d'une direction voulue vers la sortie
|
|
// on relance l'interuption pour le niveau supérieur
|
|
{ ErrSortieFinale toto;
|
|
throw (toto);
|
|
}
|
|
catch (...)//(UtilLecture::ErrNouvelleDonnee erreur)
|
|
{ cout << "\n Erreur on attendait un des mots cles proposes !!, "
|
|
<< "\n redonnez une bonne valeur"
|
|
<< "\n ou taper f ou 0 pour sortir ";
|
|
};
|
|
}; //-- fin du while
|
|
}; // fin du cas ou on veut une définition non standart
|
|
// sort << "\n# -- definition du type de deformation (par defaut: DEFORMATION_STANDART) -- "
|
|
// << "\n type_de_deformation DEFORMATION_STANDART ";
|
|
};
|
|
|
|
//----- lecture écriture de restart spécifique aux données de la classe -----
|
|
// cas donne le niveau de la récupération
|
|
// = 1 : on récupère tout
|
|
// = 2 : on récupère uniquement les données variables (supposées comme telles)
|
|
void Loi_comp_abstraite::Lecture_don_base_info(ifstream& ent,const int cas,LesReferences& lesRef
|
|
,LesCourbes1D& lesCourbes1D
|
|
,LesFonctions_nD& lesFonctionsnD)
|
|
{ string toto;
|
|
if (cas == 1)
|
|
{ // tout d'abord appel de la classe mère
|
|
LoiAbstraiteGeneral::Lect_base_info_loi(ent,cas,lesRef,lesCourbes1D,lesFonctionsnD);
|
|
// puis les infos propres
|
|
// le type de déformation
|
|
ent >> toto ;
|
|
if (toto != "type_deformation")
|
|
{ cout << "\n erreur en lecture du type de deformation, nom lu: " << toto
|
|
<< "\n Loi_comp_abstraite::Lecture_don_base_info(...";
|
|
Sortie(1);
|
|
};
|
|
// lecture des infos
|
|
ent >> toto; type_de_deformation=Id_nom_type_deformation(toto.c_str());
|
|
// lecture concernant les grandeurs particulières de liaison
|
|
{int taille=0;string nom;
|
|
ent >> toto >> taille;
|
|
listdeTouslesQuelc_dispo_localement.clear();
|
|
for (int i=1;i<=taille;i++)
|
|
{ ent >> nom;listdeTouslesQuelc_dispo_localement.push_back(Id_nomTypeQuelconque(nom));};
|
|
};
|
|
{int taille=0;string nom;
|
|
listQuelc_mis_en_acces_localement.clear();
|
|
ent >> toto >> taille;
|
|
for (int i=1;i<=taille;i++)
|
|
{ ent >> nom;listQuelc_mis_en_acces_localement.push_back(Id_nomTypeQuelconque(nom));};
|
|
};
|
|
};
|
|
ent >> toto >> temps_loi;
|
|
};
|
|
|
|
// cas donne le niveau de sauvegarde
|
|
// = 1 : on sauvegarde tout
|
|
// = 2 : on sauvegarde uniquement les données variables (supposées comme telles)
|
|
void Loi_comp_abstraite::Ecriture_don_base_info(ofstream& sort,const int cas) const
|
|
{ if (cas == 1)
|
|
{ // tout d'abord appel de la classe mère
|
|
LoiAbstraiteGeneral::Ecrit_base_info_loi(sort,cas);
|
|
// puis les infos propres
|
|
// le type de déformation
|
|
sort << " \n type_deformation " << Nom_type_deformation(type_de_deformation) << " ";
|
|
{sort << "\n list_grandeur_particuliere_dispo_localement:taille= "
|
|
<< listdeTouslesQuelc_dispo_localement.size() << " ";
|
|
list <EnumTypeQuelconque >::const_iterator il,ilfin=listdeTouslesQuelc_dispo_localement.end();
|
|
for (il=listdeTouslesQuelc_dispo_localement.begin();il != ilfin;il++)
|
|
sort << NomTypeQuelconque(*il) << " ";
|
|
};
|
|
{sort << "\n list_grandeur_particuliere_demandee_localement:taille= "
|
|
<< listQuelc_mis_en_acces_localement.size() << " ";
|
|
list <EnumTypeQuelconque >::const_iterator il,ilfin=listQuelc_mis_en_acces_localement.end();
|
|
for (il=listQuelc_mis_en_acces_localement.begin();il != ilfin;il++)
|
|
sort << NomTypeQuelconque(*il) << " ";
|
|
};
|
|
};
|
|
sort << "\n tps_cumule_loi: "<<temps_loi;
|
|
};
|
|
|
|
// activation des données des noeuds et/ou elements nécessaires au fonctionnement de la loi
|
|
// exemple: mise en service des ddl de température aux noeuds
|
|
// méthode appelée par Activation_donnees principal, ou des classes dérivées
|
|
void Loi_comp_abstraite::Activ_donnees(Tableau<Noeud *>& tabnoeud,bool dilatation,LesPtIntegMecaInterne& lesPtMecaInt)
|
|
{ if ((thermo_dependant)|| (dilatation))
|
|
{ // dans le cas où la loi est thermo dépendante on active les ddl de thermique
|
|
int nbnoeud = tabnoeud.Taille();
|
|
for (int i=1;i<=nbnoeud;i++)
|
|
{ // on vérifie que la variable TEMP existe sinon erreur
|
|
if (tabnoeud(i)->Existe_ici(TEMP))
|
|
{tabnoeud(i)->Met_en_service(TEMP);}
|
|
else
|
|
{ cout << "\n erreur: la variable temperature n'existe pas "
|
|
<< " il n'est pas possible d'utiliser une loi thermodependante "
|
|
<< " il manque sans doute des donnees !!! "
|
|
<< "\n Loi_comp_abstraite::Activ_donnees(...";
|
|
Sortie(1);
|
|
}
|
|
}
|
|
};
|
|
// cas de l'utilisation d'une fonction nD pour l'affichage
|
|
if (permet_affich_loi_nD != NULL)
|
|
{// l'objectif ici est de définir les conteneurs de grandeurs totalement quelconques
|
|
// qui seront ensuite nécessaire pour appeler la fonction
|
|
// on ne fait qu'une fois l'opération, car la fonction est appelée à chaque pti
|
|
// 1) on récupère le tableau des énumérés de quelconques de la fonction
|
|
const Tableau <EnumTypeQuelconque>& tqi = permet_affich_loi_nD->Tab_enu_quelconque();
|
|
if (tqi.Taille() != li_quelconque.size())
|
|
{// on initialise la liste
|
|
li_quelconque.clear();
|
|
// on va boucler sur les énumérés quelconque et
|
|
// créer les conteneurs de retour
|
|
int nb_tqi = tqi.Taille();
|
|
for (int i_tqi = 1;i_tqi <= nb_tqi;i_tqi++ )
|
|
// on crée les conteneurs
|
|
{EnumTypeQuelconque& enuconq = tqi(i_tqi);
|
|
switch (enuconq)
|
|
{
|
|
case CONTRAINTE_MISES :
|
|
{Grandeur_scalaire_double grand_courant(0.);
|
|
TypeQuelconque typQ1(CONTRAINTE_MISES,SIG11,grand_courant);
|
|
li_quelconque.push_back(typQ1);
|
|
break;
|
|
}
|
|
case CONTRAINTE_TRESCA :
|
|
{Grandeur_scalaire_double grand_courant(0.);
|
|
TypeQuelconque typQ1(CONTRAINTE_TRESCA,SIG11,grand_courant);
|
|
li_quelconque.push_back(typQ1);
|
|
break;
|
|
}
|
|
case CONTRAINTE_MISES_T :
|
|
{Grandeur_scalaire_double grand_courant(0.);
|
|
TypeQuelconque typQ1(CONTRAINTE_MISES_T,SIG11,grand_courant);
|
|
li_quelconque.push_back(typQ1);
|
|
break;
|
|
}
|
|
case CONTRAINTE_TRESCA_T :
|
|
{Grandeur_scalaire_double grand_courant(0.);
|
|
TypeQuelconque typQ1(CONTRAINTE_TRESCA_T,SIG11,grand_courant);
|
|
li_quelconque.push_back(typQ1);
|
|
break;
|
|
}
|
|
case NUM_ELEMENT:
|
|
{Grandeur_scalaire_entier grand_courant(0);
|
|
TypeQuelconque typQ1(NUM_ELEMENT,NU_DDL,grand_courant);
|
|
li_quelconque.push_back(typQ1);
|
|
break;
|
|
}
|
|
case NUM_MAIL_ELEM:
|
|
{Grandeur_scalaire_entier grand_courant(0);
|
|
TypeQuelconque typQ1(NUM_MAIL_ELEM,NU_DDL,grand_courant);
|
|
li_quelconque.push_back(typQ1);
|
|
break;
|
|
}
|
|
case NUM_PTI:
|
|
{Grandeur_scalaire_entier grand_courant(0);
|
|
TypeQuelconque typQ1(NUM_PTI,NU_DDL,grand_courant);
|
|
li_quelconque.push_back(typQ1);
|
|
break;
|
|
}
|
|
case REPERE_LOCAL_ORTHO :
|
|
{Coordonnee v_rep(ParaGlob::Dimension()); // un vecteur intermédiaire
|
|
Tab_Grandeur_Coordonnee gr(v_rep,3); // def d'une grandeur intermédiaire
|
|
// stockage
|
|
TypeQuelconque typQ6(REPERE_LOCAL_ORTHO,SIG11,gr);
|
|
li_quelconque.push_back(typQ6);
|
|
break;
|
|
}
|
|
case REPERE_LOCAL_H :
|
|
{Coordonnee v_rep(ParaGlob::Dimension()); // un vecteur intermédiaire
|
|
Tab_Grandeur_Coordonnee gr(v_rep,3); // def d'une grandeur intermédiaire
|
|
// stockage
|
|
TypeQuelconque typQ6(REPERE_LOCAL_H,SIG11,gr);
|
|
li_quelconque.push_back(typQ6);
|
|
break;
|
|
}
|
|
case REPERE_LOCAL_B :
|
|
{Coordonnee v_rep(ParaGlob::Dimension()); // un vecteur intermédiaire
|
|
Tab_Grandeur_Coordonnee gr(v_rep,3); // def d'une grandeur intermédiaire
|
|
// stockage
|
|
TypeQuelconque typQ6(REPERE_LOCAL_B,SIG11,gr);
|
|
li_quelconque.push_back(typQ6);
|
|
break;
|
|
}
|
|
default :
|
|
{ cout << "\n erreur dans la definition du stockage inter pour la fonction nD "
|
|
<< " d'affichage : "<< permet_affich_loi_nD->NomFonction()
|
|
<< " cas non traite: "
|
|
<< NomTypeQuelconque(enuconq) << "!\n";
|
|
cout << "\n Loi_comp_abstraite::Activ_donnees(....";
|
|
Sortie(1);
|
|
};
|
|
};
|
|
};
|
|
|
|
// on s'occupe maintenant des pointeurs
|
|
// qui seront nécessaire pour utiliser la fonction nD
|
|
if (li_quelconque.size())
|
|
{tab_pt_li_quelconque.Change_taille(li_quelconque.size());
|
|
List_io <TypeQuelconque >::iterator ili,ilifin = li_quelconque.end();
|
|
int i=1; // init
|
|
for (ili= li_quelconque.begin();ili != ilifin; ili++,i++)
|
|
tab_pt_li_quelconque(i) = &(*ili);
|
|
};
|
|
};
|
|
};
|
|
|
|
};
|
|
|
|
// ***** a supprimer à terme, -> écriture d'un message d'erreur ******
|
|
// calcul des contraintes et ses variations par rapport aux déformations a t+dt
|
|
// en_base_orthonormee: le tenseur de contrainte en entrée est en orthonormeee
|
|
// le tenseur de déformation et son incrémentsont également en orthonormees
|
|
// si = false: les bases transmises sont utilisées
|
|
// ex: contient les éléments de métrique relativement au paramétrage matériel = X_(0)^a
|
|
void Loi_comp_abstraite::Calcul_dsigma_deps
|
|
(bool en_base_orthonormee, TenseurHH & ,TenseurBB&
|
|
,TenseurBB & ,TenseurBB & ,double& ,double&
|
|
,TenseurHH& ,TenseurHHHH&
|
|
,EnergieMeca & ,const EnergieMeca & ,double& , double& ,const Met_abstraite::Umat_cont&
|
|
)
|
|
|
|
{ cout << "\n ERREUR: methode non encore implante !!!!"
|
|
<< "\n methode Loi_comp_abstraite::Calcul_dsigma_deps (...";
|
|
Affiche();
|
|
Sortie(1);
|
|
};
|
|
|
|
|
|
// calcul éventuel des invariants liés aux contraintes
|
|
void Loi_comp_abstraite::CalculInvariants_contraintes
|
|
(PtIntegMecaInterne& ptIntegMeca, TenseurBB & gijBB,TenseurHH & gijHH)
|
|
{ // def de la dimension des tenseurs
|
|
int dimT = ptIntegMeca.EpsBB()->Dimension();
|
|
int caas=0; // pour la gestion d'erreur éventuelle
|
|
// on calcul maintenant systématiquement les contraintes de Mises et Tresca
|
|
TenseurHB& sigHB = *(NevezTenseurHB(dimT)) ;
|
|
sigHB = (*(ptIntegMeca.SigHH()) * gijBB);
|
|
// calcul de Mises et Tresca
|
|
Coordonnee valPropreSig(sigHB.ValPropre(caas));
|
|
if (caas == -1)
|
|
{cout << "\n *** erreur dans le calcul des valeurs propres de sigma "
|
|
<< " pb eventuel si on doit ensuite les utiliser (dans une fonction nD par exemple) "
|
|
<< " on continue neanmoins ...";
|
|
cout << "\n Loi_comp_abstraite::CalculInvariants_contraintes(..." << flush;
|
|
};
|
|
|
|
Tableau <double>& tab_sig_equi = ptIntegMeca.Sig_equi();
|
|
Coordonnee& vv = valPropreSig; int dimvec=vv.Dimension();// pour condenser l'écriture
|
|
double& sig_mises = tab_sig_equi(1); // pour être plus explicite
|
|
double& Tresca = tab_sig_equi(2); // "
|
|
switch (dimvec) // dans le cas où dimvec=0 on ne fait rien, cas ou on n'a pas besoin de mises
|
|
{ case 1: sig_mises = Dabs(vv(1)); Tresca=0.5 * vv(1);
|
|
break;
|
|
case 2: sig_mises = sqrt( ((vv(1)-vv(2))*(vv(1)-vv(2)) + vv(1) * vv(1)
|
|
+ vv(2) * vv(2)) * 0.5);
|
|
Tresca=0.5 * (vv(1)-vv(2));
|
|
break;
|
|
case 3: sig_mises = sqrt( ((vv(1)-vv(2))*(vv(1)-vv(2)) + (vv(1)-vv(3))*(vv(1)-vv(3))
|
|
+ (vv(3)-vv(2))*(vv(3)-vv(2))) * 0.5);
|
|
Tresca=0.5 * (vv(1)-vv(3));
|
|
break;
|
|
default: cout << "\n erreur de dimension, ne doit pas arriver ?? "
|
|
<< "\n Loi_comp_abstraite::CalculInvariants_contraintes(..." << flush;
|
|
Sortie(1);
|
|
};
|
|
|
|
// calcul éventuel des invariants
|
|
if (ptIntegMeca.Statut_Invariants_contrainte())
|
|
{ Vecteur & invariant = ptIntegMeca.SigInvar();
|
|
invariant.Change_taille(Abs(dimT));
|
|
switch (abs(dimT))
|
|
{case 3: invariant(3)= sigHB.Det();
|
|
case 2: invariant(2)= sigHB.II();
|
|
case 1: invariant(1)= sigHB.Trace();
|
|
};
|
|
|
|
////----- debug
|
|
////if ((invariant(1) > 0.) && ((*(ptIntegMeca.SigHH()))(1,1) < 0.))
|
|
// { cout << "\n Loi_comp_abstraite::CalculInvariants "
|
|
// << " invariant(1)= "<<invariant(1)<< ", (*(ptIntegMeca.SigHH()))(1,1)= "<< (*(ptIntegMeca.SigHH()))(1,1)
|
|
// << endl;
|
|
// };
|
|
////--- fin debug
|
|
};
|
|
|
|
TenseurHB * ptHB = &sigHB; delete ptHB;
|
|
|
|
};
|
|
|
|
// calcul éventuel des invariants liés uniquement à la cinématique
|
|
void Loi_comp_abstraite::CalculInvariants_cinematique
|
|
(PtIntegMecaInterne& ptIntegMeca, TenseurBB & gijBB,TenseurHH & gijHH)
|
|
{ // def de la dimension des tenseurs
|
|
int dimT = ptIntegMeca.EpsBB()->Dimension();
|
|
int caas=0; // pour la gestion d'erreur éventuelle
|
|
|
|
if (ptIntegMeca.Statut_Invariants_deformation())
|
|
{ TenseurHB& epsHB = *(NevezTenseurHB(dimT)) ;
|
|
epsHB = gijHH * (*(ptIntegMeca.EpsBB()));
|
|
Vecteur & invariant = ptIntegMeca.EpsInvar();
|
|
invariant.Change_taille(Abs(dimT));
|
|
switch (abs(dimT))
|
|
{case 3: invariant(3)= epsHB.Det();
|
|
case 2: invariant(2)= epsHB.II();
|
|
case 1: invariant(1)= epsHB.Trace();
|
|
};
|
|
// ptIntegMeca.EpsInvar() = epsHB.ValPropre(caas);
|
|
// if (caas == -1)
|
|
// { cout << "\n warning *** erreur dans le calcul des valeurs propres de la deformation";
|
|
// if (ParaGlob::NiveauImpression() >= 7) {epsHB.Ecriture(cout); cout << "\nLoi_comp_abstraite::CalculInvariants(...";};
|
|
// cout << endl;
|
|
// };
|
|
TenseurHB * ptHB = &epsHB; delete ptHB;
|
|
};
|
|
if (ptIntegMeca.Statut_Invariants_vitesseDeformation())
|
|
{ TenseurHB& DepsHB = *(NevezTenseurHB(dimT)) ;
|
|
DepsHB = gijHH * (*(ptIntegMeca.DepsBB()));
|
|
Vecteur & invariant = ptIntegMeca.DepsInvar();
|
|
invariant.Change_taille(Abs(dimT));
|
|
switch (abs(dimT))
|
|
{case 3: invariant(3)= DepsHB.Det();
|
|
case 2: invariant(2)= DepsHB.II();
|
|
case 1: invariant(1)= DepsHB.Trace();
|
|
};
|
|
TenseurHB * ptHB = &DepsHB; delete ptHB;
|
|
// ptIntegMeca.DepsInvar() = DepsHB.ValPropre(caas);
|
|
// if (caas == -1)
|
|
// { cout << "\n warning *** erreur dans le calcul des valeurs propres de la vitesse de deformation";
|
|
// if (ParaGlob::NiveauImpression() >= 7) {DepsHB.Ecriture(cout); cout << "\nLoi_comp_abstraite::CalculInvariants(...";};
|
|
// cout << endl;
|
|
// };
|
|
};
|
|
};
|
|
|
|
|
|
|
|
// récupération de valeurs interpolées pour les grandeur enu ou directement calculées
|
|
// absolue: indique si oui ou non on sort les tenseurs dans la base absolue ou une base particulière
|
|
// une seule des 3 métriques doit-être renseigné, les autres doivent être un pointeur nul
|
|
// exclure_dd_etend: donne une liste de Ddl_enum_etendu à exclure de la recherche
|
|
// parce que par exemple, ils sont calculés par ailleurs
|
|
// on peut également ne pas définir de métrique, dans ce cas on ne peut pas calculer certaines grandeurs
|
|
// -> il y a vérification
|
|
Tableau <double> Loi_comp_abstraite::Valeur_multi_interpoler_ou_calculer
|
|
(bool absolue, Enum_dure temps,const List_io<Ddl_enum_etendu>& enu
|
|
,const Met_abstraite::Impli* ex_impli
|
|
,const Met_abstraite::Expli_t_tdt* ex_expli_tdt
|
|
,const Met_abstraite::Umat_cont* ex_umat
|
|
,const List_io<Ddl_enum_etendu>* exclure_dd_etend
|
|
)
|
|
{ // on a besoin a priori de ptintmeca_en_cours, donc s'il n'est pas définit -> erreur
|
|
#ifdef MISE_AU_POINT
|
|
if (ptintmeca_en_cours == NULL)
|
|
{cout << "\n *** cas non prevu : aucun conteneur de point d'integration transmis "
|
|
<< "\n Loi_comp_abstraite::Valeur_multi_interpoler_ou_calculer(..." << endl;
|
|
Sortie(1);
|
|
};
|
|
if (def_en_cours == NULL)
|
|
{cout << "\n *** cas non prevu : la deformation n'est pas transmise "
|
|
<< "\n Loi_comp_abstraite::Valeur_multi_interpoler_ou_calculer(..." << endl;
|
|
Sortie(1);
|
|
};
|
|
#endif
|
|
// 2) le fait que l'on veut une sortie dans une base ad hoc ou pas
|
|
int dim = ptintmeca_en_cours->EpsBB_const().Dimension();
|
|
int dim_sortie_tenseur = dim;
|
|
// dans le cas ou l'on veut une sortie en base absolue, il faut que dim_sortie_tenseur = la dimension de la base absolue
|
|
if (absolue)
|
|
dim_sortie_tenseur = ParaGlob::Dimension();
|
|
// --- pour ne faire qu'un seul test ensuite
|
|
bool prevoir_change_dim_tenseur = false;
|
|
if (absolue)
|
|
// mais en fait, quand on sort en absolu on est obligé d'utiliser un tenseur intermédiaire
|
|
// car BaseAbsolue(.. modifie tenseur passé en paramètre, donc dans tous les cas de sortie absolue
|
|
// il faut un tenseur intermédiaire qui a ou non une dimension différente
|
|
prevoir_change_dim_tenseur = true;
|
|
// recup de l'incrément de temps
|
|
double deltat=ParaGlob::Variables_de_temps().IncreTempsCourant();
|
|
double unSurDeltat=0;
|
|
if (Abs(deltat) >= ConstMath::trespetit)
|
|
{unSurDeltat = 1./deltat;}
|
|
else // si l'incrément de temps est tres petit on remplace 1/deltat par un nombre tres grand
|
|
{ // un pas de temps doit être positif !! or certaine fois il peut y avoir des pb
|
|
if (unSurDeltat < 0)
|
|
{ cout << "\n le pas de temps est négatif !! "; };
|
|
unSurDeltat = ConstMath::tresgrand;
|
|
};
|
|
|
|
// -- def des tenseurs locaux
|
|
Coordonnee* Mtdt = NULL; // coordonnées finales éventuelles du point d'intégration considéré
|
|
Coordonnee* Mt=NULL; // coordonnées à t
|
|
Coordonnee* M0 = NULL; // coordonnées initiales éventuelles du point d'intégration considéré
|
|
Coordonnee* N_surf = NULL; // coordonnée d'un vecteur normal actuel si c'est adéquate
|
|
Coordonnee* N_surf_t = NULL; // coordonnée d'un vecteur normal à t si c'est adéquate
|
|
Coordonnee* N_surf_t0 = NULL; // coordonnée d'un vecteur normal à t0 si c'est adéquate
|
|
Coordonnee* Vitesse = NULL; // cas des vitesses
|
|
|
|
Tableau <double> tab_ret (enu.size());
|
|
|
|
// éléments de métrique et matrices de passage
|
|
TenseurHH* gijHH;TenseurBB* gijBB;BaseB* giB; BaseH* giH_0;BaseH* giH;
|
|
BaseB* giB_0;BaseB* giB_t;
|
|
Mat_pleine jB0(dim,dim),jBfin(dim,dim);
|
|
bool pas_de_metrique_dispo = false; // init
|
|
|
|
if (ex_impli != NULL)
|
|
{ gijHH = ex_impli->gijHH_tdt;gijBB = ex_impli->gijBB_tdt;
|
|
giB = ex_impli->giB_tdt; giH_0 = ex_impli->giH_0;giH = ex_impli->giH_tdt;
|
|
giB_0 = ex_impli->giB_0;giB_t = ex_impli->giB_t;
|
|
}
|
|
else if (ex_expli_tdt != NULL)
|
|
{gijHH = ex_expli_tdt->gijHH_tdt;gijBB = ex_expli_tdt->gijBB_tdt;
|
|
giB = ex_expli_tdt->giB_tdt; giH_0 = ex_expli_tdt->giH_0;giH = ex_expli_tdt->giH_tdt;
|
|
giB_0 = ex_expli_tdt->giB_0; giB_t = ex_expli_tdt->giB_t;
|
|
}
|
|
else if (ex_umat != NULL)
|
|
{gijHH = ex_umat->gijHH_t;gijBB = ex_umat->gijBB_t;
|
|
giB = giB_t = ex_umat->giB_t; giH_0 = ex_umat->giH_0;giH = ex_umat->giH_t;
|
|
giB_0 = ex_umat->giB_0;
|
|
}
|
|
else
|
|
{ pas_de_metrique_dispo = true;
|
|
// cout << "\n *** cas non prevu : aucune metrique transmise "
|
|
// << "\n Loi_comp_abstraite::Valeur_multi_interpoler_ou_calculer(..." << endl;
|
|
// Sortie(1);
|
|
};
|
|
|
|
// on définie des indicateurs pour ne pas faire plusieurs fois le même calcul
|
|
List_io<Ddl_enum_etendu>::const_iterator ie,iefin=enu.end();
|
|
bool besoin_coordonnees = false; bool besoin_deplacements = false;
|
|
bool besoin_coordonnees_t = false;bool besoin_coordonnees_t0 = false;
|
|
for (ie=enu.begin(); ie!=iefin;ie++)
|
|
{ int posi = (*ie).Position()-NbEnum_ddl();
|
|
switch (posi)
|
|
{
|
|
case 114: case 115: case 116: // le vecteur normal
|
|
{ N_surf = new Coordonnee(ParaGlob::Dimension()); break;}
|
|
case 117: case 118: case 119: // le vecteur normal à t
|
|
{ N_surf_t = new Coordonnee(ParaGlob::Dimension()); break;}
|
|
case 120: case 121: case 122: // le vecteur normal à t0
|
|
{ N_surf_t0 = new Coordonnee(ParaGlob::Dimension()); break;}
|
|
|
|
case 123: case 124: case 125: // la position à t
|
|
{ Mt = new Coordonnee(ParaGlob::Dimension());
|
|
besoin_coordonnees_t = true;
|
|
break;
|
|
}
|
|
case 126: case 127: case 128: // la position à t0
|
|
{ M0 = new Coordonnee(ParaGlob::Dimension());
|
|
besoin_coordonnees_t0 = true;
|
|
break;
|
|
}
|
|
default:
|
|
break;
|
|
};
|
|
};
|
|
|
|
// définition des tenseurs si nécessaire
|
|
|
|
|
|
// ----- maintenant on calcule les grandeurs nécessaires -----
|
|
if (besoin_coordonnees)
|
|
{Mtdt = new Coordonnee(ParaGlob::Dimension());
|
|
*Mtdt = def_en_cours->Position_tdt();
|
|
};
|
|
if (besoin_coordonnees_t )
|
|
{*Mt = def_en_cours->Position_tdt();
|
|
};
|
|
if (besoin_deplacements || besoin_coordonnees_t0)
|
|
{if (M0 == NULL)
|
|
M0 = new Coordonnee(ParaGlob::Dimension());
|
|
(*M0) = def_en_cours->Position_0();
|
|
};
|
|
if (Vitesse != NULL)
|
|
{Vitesse = new Coordonnee(ParaGlob::Dimension());
|
|
(*Vitesse) = def_en_cours->VitesseM_tdt();
|
|
};
|
|
|
|
// def éventuelle du vecteur normal: ceci n'est correct qu'avec une métrique 2D
|
|
if (N_surf != NULL)
|
|
{ if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur N_surf necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
|
|
// on vérifie que la métrique est correcte
|
|
if (giB->NbVecteur() != 2)
|
|
{if (ParaGlob::NiveauImpression() > 0)
|
|
{cout << "\n *** attention il ne s'agit pas d'une metrique 2D 2D,"
|
|
<< " le vecteur normal ne sera pas correctement calcule";
|
|
if (ParaGlob::NiveauImpression() > 2)
|
|
cout << "\n Loi_comp_abstraite::Valeur_multi_interpoler_ou_calculer(... ";
|
|
};
|
|
cout << endl;
|
|
}
|
|
else // sinon c'est ok
|
|
{// la normale vaut le produit vectoriel des 2 premiers vecteurs
|
|
(*N_surf) = Util::ProdVec_coorBN( (*giB)(1), (*giB)(2));
|
|
N_surf->Normer(); // que l'on norme
|
|
};
|
|
};
|
|
// idem à l'instant t
|
|
if (N_surf_t != NULL)
|
|
{ if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur N_surf_t necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
// on vérifie que la métrique est correcte
|
|
if (giB_t->NbVecteur() != 2)
|
|
{if (ParaGlob::NiveauImpression() > 0)
|
|
{cout << "\n *** attention il ne s'agit pas d'une metrique 2D 2D,"
|
|
<< " le vecteur normal ne sera pas correctement calcule";
|
|
if (ParaGlob::NiveauImpression() > 2)
|
|
cout << "\n Loi_comp_abstraite::Valeur_multi_interpoler_ou_calculer(... ";
|
|
};
|
|
cout << endl;
|
|
}
|
|
else // sinon c'est ok
|
|
{// la normale vaut le produit vectoriel des 2 premiers vecteurs
|
|
(*N_surf_t) = Util::ProdVec_coorBN( (*giB_t)(1), (*giB_t)(2));
|
|
N_surf_t->Normer(); // que l'on norme
|
|
};
|
|
};
|
|
// idem à l'instant t0
|
|
if (N_surf_t0 != NULL)
|
|
{ if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur N_surf_0 necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
// on vérifie que la métrique est correcte
|
|
if (giB_0->NbVecteur() != 2)
|
|
{if (ParaGlob::NiveauImpression() > 0)
|
|
{cout << "\n *** attention il ne s'agit pas d'une metrique 2D 2D,"
|
|
<< " le vecteur normal ne sera pas correctement calcule";
|
|
if (ParaGlob::NiveauImpression() > 2)
|
|
cout << "\n Loi_comp_abstraite::Valeur_multi_interpoler_ou_calculer(... ";
|
|
};
|
|
cout << endl;
|
|
}
|
|
else // sinon c'est ok
|
|
{// la normale vaut le produit vectoriel des 2 premiers vecteurs
|
|
(*N_surf_t0) = Util::ProdVec_coorBN( (*giB_0)(1), (*giB_0)(2));
|
|
N_surf_t0->Normer(); // que l'on norme
|
|
};
|
|
// on n'arrête pas l'exécution, car on pourrait vouloir sortir les normales pour un ensemble
|
|
// d'éléments contenant des volumes, des surfaces, des lignes: bon... il y aura quand même des
|
|
// pb au niveau des iso par exemple, du au fait que l'on va faire des moyennes sur des éléments
|
|
// de type différents (à moins de grouper par type du coup on n'aura pas le warning
|
|
};
|
|
//----- fin du calcul des grandeurs nécessaires -----
|
|
|
|
|
|
// init pour l'utilisation de la liste d'exclusion
|
|
List_io<Ddl_enum_etendu>::const_iterator itt_deb;
|
|
List_io<Ddl_enum_etendu>::const_iterator itt_fin;
|
|
if (exclure_dd_etend != NULL)
|
|
{ itt_deb = exclure_dd_etend->begin();
|
|
itt_fin = exclure_dd_etend->end();
|
|
};
|
|
|
|
// on balaie maintenant la liste des grandeurs à sortir
|
|
int it; // it est l'indice dans le tableau de retour
|
|
for (it=1,ie=enu.begin(); ie!=iefin;ie++,it++)
|
|
{ if ((Meme_famille((*ie).Enum(),SIG11)) || (Meme_famille((*ie).Enum(),EPS11))
|
|
|| (Meme_famille((*ie).Enum(),DEPS11)) || (Meme_famille((*ie).Enum(),X1))
|
|
|| (Meme_famille((*ie).Enum(),UX)) )
|
|
{ // on recherche en générale une interpolation en fonction des noeuds: il faut donc que la grandeur soit
|
|
// présente aux noeuds !!
|
|
// def du numéro de référence du ddl_enum_etendue
|
|
int posi = (*ie).Position()-NbEnum_ddl();
|
|
// récupération des informations en fonction des différents cas
|
|
// **** 1 >>>>> -- cas des ddl pur, que l'on sort dans le repère global par défaut
|
|
// cas des contraintes
|
|
if ((Meme_famille((*ie).Enum(),SIG11)) && ((*ie).Nom_vide()))
|
|
{ tab_ret(it)= def_en_cours->DonneeInterpoleeScalaire((*ie).Enum(),temps);
|
|
}
|
|
else if ((Meme_famille((*ie).Enum(),EPS11)) && ((*ie).Nom_vide()))
|
|
{ tab_ret(it)= def_en_cours->DonneeInterpoleeScalaire((*ie).Enum(),temps);
|
|
}
|
|
else if ((Meme_famille((*ie).Enum(),DEPS11)) && ((*ie).Nom_vide()))
|
|
{ tab_ret(it)= def_en_cours->DonneeInterpoleeScalaire((*ie).Enum(),temps);
|
|
}
|
|
else if ((Meme_famille((*ie).Enum(),X1)) && ((*ie).Nom_vide()))
|
|
{ tab_ret(it)= (*Mtdt)((*ie).Enum() - X1 +1);
|
|
}
|
|
else if ((Meme_famille((*ie).Enum(),UX)) && ((*ie).Nom_vide()))
|
|
{ int i_cor = (*ie).Enum() - UX +1; // l'indice de coordonnée
|
|
tab_ret(it)= (*Mtdt)(i_cor) - (*M0)(i_cor);
|
|
}
|
|
else if ((Meme_famille((*ie).Enum(),V1)) && ((*ie).Nom_vide()))
|
|
{ int i_cor = (*ie).Enum() - V1 +1; // l'indice de coordonnée
|
|
tab_ret(it)= (*Vitesse)(i_cor);
|
|
}
|
|
// --- a complèter ----
|
|
|
|
else
|
|
{// **** 2 >>>>> -- cas des grandeurs déduites des ddl pures
|
|
switch (posi)
|
|
{ case 31: /*contrainte_mises*/
|
|
tab_ret(it)=ptintmeca_en_cours->Sig_equi_const()(1);break;
|
|
case 32: /* contrainte_tresca */
|
|
tab_ret(it)=ptintmeca_en_cours->Sig_equi_const()(2);break;
|
|
|
|
case 77: /*def_duale_mises*/ tab_ret(it)=ptintmeca_en_cours->Deformation_equi_const()(2);break;
|
|
case 87: /*def_equivalente*/ tab_ret(it)=ptintmeca_en_cours->Deformation_equi_const()(1);break;
|
|
case 88: /*def_duale_mises_maxi*/ tab_ret(it)=ptintmeca_en_cours->Deformation_equi_const()(3);break;
|
|
case 89: /*vitesse_def_equivalente*/ tab_ret(it)=ptintmeca_en_cours->Deformation_equi_const()(4) * unSurDeltat;break;
|
|
|
|
case 114: // le vecteur normal N_surf_1
|
|
{tab_ret(it)= (*N_surf)(1);break;}
|
|
case 115: // le vecteur normal N_surf_2
|
|
{tab_ret(it)= (*N_surf)(2);break;}
|
|
case 116: // le vecteur normal N_surf_3
|
|
{tab_ret(it)= (*N_surf)(3);break;}
|
|
case 117: // le vecteur normal N_surf_1_t
|
|
{tab_ret(it)= (*N_surf_t)(1);break;}
|
|
case 118: // le vecteur normal N_surf_2_t
|
|
{tab_ret(it)= (*N_surf_t)(2);break;}
|
|
case 119: // le vecteur normal N_surf_3_t
|
|
{tab_ret(it)= (*N_surf_t)(3);break;}
|
|
case 120: // le vecteur normal N_surf_1_t0
|
|
{tab_ret(it)= (*N_surf_t0)(1);break;}
|
|
case 121: // le vecteur normal N_surf_2_t0
|
|
{tab_ret(it)= (*N_surf_t0)(2);break;}
|
|
case 122: // le vecteur normal N_surf_3_t0
|
|
{tab_ret(it)= (*N_surf_t0)(3);break;}
|
|
case 123: // la position géométrique Mt
|
|
{tab_ret(it)= (*Mt)(1);break;}
|
|
case 124: // la position géométrique Mt
|
|
{tab_ret(it)= (*Mt)(2);break;}
|
|
case 125: // la position géométrique Mt
|
|
{tab_ret(it)= (*Mt)(3);break;}
|
|
case 126: // la position géométrique M0
|
|
{tab_ret(it)= (*M0)(1);break;}
|
|
case 127: // la position géométrique M0
|
|
{tab_ret(it)= (*M0)(2);break;}
|
|
case 128: // la position géométrique M0
|
|
{tab_ret(it)= (*M0)(3);break;}
|
|
|
|
default :
|
|
{// on regarde si la grandeur en fait n'est pas à calculer
|
|
bool a_atraiter = true;
|
|
if (exclure_dd_etend != NULL)
|
|
if (find(itt_deb,itt_fin,(*ie)) != itt_fin)
|
|
a_atraiter = false;
|
|
if (a_atraiter)
|
|
{cout << "\n cas de ddl actuellement non traite "
|
|
<< "\n pas de ddl " << (*ie).Nom() << " dans l'element "
|
|
<< "\n ou cas non implante pour l'instant"
|
|
<< "\n Loi_comp_abstraite::Valeur_multi_interpoler_ou_calculer(...";
|
|
tab_ret(it) = 0.;
|
|
};
|
|
};
|
|
} // fin cas **** 2 >>>>>
|
|
} // " " "
|
|
} // -- fin
|
|
else if (( (*ie).Enum() == TEMP) && ((*ie).Nom_vide()))
|
|
{tab_ret(it)= def_en_cours->DonneeInterpoleeScalaire(TEMP,temps);
|
|
}
|
|
else
|
|
{ tab_ret(it) = 0.;
|
|
cout << "\n cas de ddl actuellement non traite "
|
|
<< "\n pas de ddl " << (*ie).Nom() << " dans l'element "
|
|
<< "\n ou cas non implante pour l'instant, on retourne 0"
|
|
<< "\n Loi_comp_abstraite::Valeur_multi_interpoler_ou_calculer(...";
|
|
};
|
|
};// -- fin de la boucle sur la liste de Ddl_enum_etendu
|
|
|
|
// delet e des tenseurs
|
|
if (Mtdt != NULL) delete Mtdt; // coordonnée du point à tdt
|
|
if (Mt != NULL ) delete Mt; // la position à t
|
|
if (M0 != NULL ) delete M0; // coordonnée du point à 0
|
|
if (N_surf != NULL) delete N_surf; // vecteur normal à la surface
|
|
if (N_surf_t != NULL) delete N_surf_t; // vecteur normal à t à la surface
|
|
if (N_surf_t0 != NULL) delete N_surf_t0; // vecteur normal à la surface
|
|
if (Vitesse != NULL) delete Vitesse; // vitesse
|
|
// liberation des tenseurs intermediaires
|
|
LibereTenseur();
|
|
return tab_ret;
|
|
};
|
|
|
|
// affichage de la liste des grandeurs possible à calculer avec Valeur_multi_interpoler_ou_calculer
|
|
void Loi_comp_abstraite::Affichage_grandeurs_Valeur_multi_interpoler_ou_calculer()
|
|
{ cout << "\n grandeurs scalaires disponibles :";
|
|
cout << "\n Mtdt(i) -> X1, X2 ..., Mt(i) -> X1_t, X2_t ..., M0(i) -> X1_t0, X2_t0..,"
|
|
<< "\n si pertinent: N_surf(i) -> N_surf_1.., N_surf_t(i) -> N_surf_1_t.., N_surf_t0(i) -> N_surf_1_t0..."
|
|
<< "\n SIG11 SIG12 ..., EPS11, EPS12 ..., UX, UY, UZ , V1,V2,V3"
|
|
<< "\n def_duale_mises, def_equivalente, def_duale_mises_maxi, vitesse_def_equivalente"
|
|
<< "\n contrainte de Mises, contrainte de Tresca"
|
|
<< "\n temperature -> TEMP "
|
|
;
|
|
};
|
|
|
|
// récupération de valeurs interpolées pour les grandeur enu
|
|
// absolue: indique si oui ou non on sort les tenseurs dans la base absolue ou une base particulière
|
|
// une seule des 3 métriques doit-être renseigné, les autres doivent être un pointeur nul
|
|
// exclure_Q: donne une liste de grandeur quelconque à exclure de la recherche
|
|
// parce que par exemple, ils sont calculés par ailleurs
|
|
// on peut également ne pas définir de métrique, dans ce cas on ne peut pas calculer certaines grandeurs
|
|
// -> il y a vérification
|
|
void Loi_comp_abstraite::Valeurs_Tensorielles_interpoler_ou_calculer
|
|
(bool absolue, Enum_dure temps,List_io<TypeQuelconque>& enu
|
|
,const Met_abstraite::Impli* ex_impli
|
|
,const Met_abstraite::Expli_t_tdt* ex_expli_tdt
|
|
,const Met_abstraite::Umat_cont* ex_umat
|
|
,const List_io<EnumTypeQuelconque>* exclure_Q
|
|
)
|
|
|
|
// la dimension des tenseurs de retour est obligatoirement celle de l'espace
|
|
// Dans le cas ou on veut une base ad hoc, on calcule dans la base ad hoc et on
|
|
// transfert dans le conteneur: ainsi dans ce cas seule les composantes de la base
|
|
// ad hoc sont alimentées:
|
|
// exemple: base ad hoc : dim 1, espace 3 -> eps11 sera stocké dans le conteneur
|
|
// en 11, les autres seront nulles
|
|
|
|
{ // on a besoin a priori de ptintmeca_en_cours, donc s'il n'est pas définit -> erreur
|
|
#ifdef MISE_AU_POINT
|
|
if (ptintmeca_en_cours == NULL)
|
|
{cout << "\n *** cas non prevu : aucun conteneur de point d'integration transmis "
|
|
<< "\n Loi_comp_abstraite::Valeurs_Tensorielles_interpoler_ou_calculer(..." << endl;
|
|
Sortie(1);
|
|
};
|
|
if (def_en_cours == NULL)
|
|
{cout << "\n *** cas non prevu : la deformation n'est pas transmise "
|
|
<< "\n Loi_comp_abstraite::Valeurs_Tensorielles_interpoler_ou_calculer(..." << endl;
|
|
Sortie(1);
|
|
};
|
|
#endif
|
|
// ----- def de grandeurs de travail
|
|
// def de la dimension des tenseurs
|
|
// il y a deux pb a gérer: 1) le fait que la dimension absolue peut-être différente de la dimension actuelle des tenseurs calculés
|
|
// 2) le fait que l'on veut une sortie dans une base ad hoc ou pas
|
|
// 3) le fait que les conteneurs de retour peuvent ne pas avoir la dimension voulue
|
|
int dim = ptintmeca_en_cours->EpsBB_const().Dimension(); // == a dimension actuelle des tenseurs calculés
|
|
int dim_sortie_tenseur = dim; // init
|
|
// dans le cas ou l'on veut une sortie en base absolue, il faut que dim_sortie_tenseur = la dimension de la base absolue
|
|
int dim_espace = ParaGlob::Dimension();
|
|
if (absolue)
|
|
dim_sortie_tenseur = dim_espace;
|
|
// pour ne faire qu'un seul test ensuite
|
|
bool prevoir_change_dim_tenseur = false;
|
|
// initialement on faisait le test suivant,
|
|
// if ((absolue) && (dim != dim_sortie_tenseur))
|
|
if (absolue)
|
|
// mais en fait, quand on sort en absolu on est obligé d'utiliser un tenseur intermédiaire
|
|
// car BaseAbsolue(.. modifie tenseur passé en paramètre, donc dans tous les cas de sortie absolue
|
|
// il faut un tenseur intermédiaire qui a ou non une dimension différente
|
|
prevoir_change_dim_tenseur = true;
|
|
|
|
// si on n'est pas en absolue, donc on est en ad hoc (c'est l'un ou l'autre)
|
|
// et si la dim ad hoc est différente de dim_espace, alors il faut aussi
|
|
// un tenseur intermédiaire mais de dim ad hoc
|
|
bool transfert_tenseur = false;
|
|
if ((!absolue)&&(dim != dim_espace))
|
|
{dim_sortie_tenseur = dim; // la dimension des tenseurs intermédiaires créés
|
|
transfert_tenseur = true;
|
|
}
|
|
|
|
|
|
// éléments de métrique et matrices de passage
|
|
TenseurHH* gijHH;TenseurBB* gijBB;BaseB* giB; BaseH* giH_0;BaseH* giH;
|
|
Mat_pleine jB0(dim,dim),jBfin(dim,dim);
|
|
BaseB* giB_0;BaseB* giB_t;
|
|
bool pas_de_metrique_dispo = false; // init
|
|
|
|
if (ex_impli != NULL)
|
|
{ gijHH = ex_impli->gijHH_tdt;gijBB = ex_impli->gijBB_tdt;
|
|
giB = ex_impli->giB_tdt; giH_0 = ex_impli->giH_0;giH = ex_impli->giH_tdt;
|
|
giB_t = ex_impli->giB_t; giB_0 = ex_impli->giB_0;
|
|
}
|
|
else if (ex_expli_tdt != NULL)
|
|
{gijHH = ex_expli_tdt->gijHH_tdt;gijBB = ex_expli_tdt->gijBB_tdt;
|
|
giB = ex_expli_tdt->giB_tdt; giH_0 = ex_expli_tdt->giH_0;giH = ex_expli_tdt->giH_tdt;
|
|
giB_t = ex_expli_tdt->giB_t; giB_0 = ex_expli_tdt->giB_0;
|
|
}
|
|
else if (ex_umat != NULL)
|
|
{gijHH = ex_umat->gijHH_t;gijBB = ex_umat->gijBB_t;
|
|
giB = giB_t = ex_umat->giB_t; giH_0 = ex_umat->giH_0;giH = ex_umat->giH_t;
|
|
giB_0 = ex_umat->giB_0;
|
|
}
|
|
else
|
|
{ pas_de_metrique_dispo = true;
|
|
};
|
|
|
|
|
|
// def de tenseurs pour la sortie
|
|
// les tenseurs restants en locale
|
|
TenseurHH* sigHH=NULL;TenseurBB* epsBB=NULL;TenseurBB* epslogBB=NULL;
|
|
TenseurBB* epsAlmBB=NULL;TenseurBB* eps0BB=NULL;TenseurBB* DepsBB = NULL;
|
|
TenseurBB* epsAlmTotalBB=NULL;TenseurBB* epsGLTotalBB=NULL;TenseurBB* epsLogTotalBB=NULL;
|
|
TenseurBB* DeltaEpsBB = NULL;
|
|
|
|
Coordonnee* Mtdt=NULL; // coordonnées éventuelles du point d'intégration considéré
|
|
Coordonnee* Mt=NULL; // coordonnées à t
|
|
Coordonnee* M0=NULL; // coordonnées à t0
|
|
Coordonnee* N_surf = NULL; // coordonnée d'un vecteur normal si c'est adéquate
|
|
Coordonnee* N_surf_t = NULL; // coordonnée d'un vecteur normal à t si c'est adéquate
|
|
Coordonnee* N_surf_t0 = NULL; // coordonnée d'un vecteur normal à t0 si c'est adéquate
|
|
Coordonnee* Vitesse = NULL; // cas des vitesses
|
|
Coordonnee* Deplacement = NULL; // cas du déplacement
|
|
|
|
// pour les valeurs propres
|
|
Coordonnee* valPropreSig=NULL;Coordonnee* valPropreEps=NULL;
|
|
Coordonnee* valPropreDeps=NULL;
|
|
|
|
// pour les vecteurs propres
|
|
Tableau <Coordonnee *> base_propre_sigma , base_propre_eps , base_propre_D;
|
|
|
|
// pour les bases
|
|
Tableau <Coordonnee *> base_ad_hoc , base_giH , base_giB;
|
|
|
|
// grandeurs scalaires
|
|
|
|
// grandeurs scalaires
|
|
double* Mises = NULL; double* defDualMises = NULL; double* Tresca = NULL;
|
|
double* erreur = NULL;double* erreur_rel = NULL;
|
|
double* spherique_eps=NULL,* Q_eps=NULL,* cos3phi_eps=NULL;
|
|
double* spherique_sig=NULL,* Q_sig=NULL,* cos3phi_sig=NULL;
|
|
double* spherique_Deps=NULL,* Q_Deps=NULL,* cos3phi_Deps=NULL;
|
|
double* def_equivalente=NULL, * defDualMisesMaxi=NULL;
|
|
|
|
double* sig_mises= NULL; // *** peut-être en trop
|
|
double* sig_tresca = NULL; // *** peut-être en trop
|
|
|
|
// --- dev d'un ensemble de variable booléenne pour gérer les sorties en une passe -----
|
|
// on se réfère au informations définit dans la méthode: Les_type_evolues_internes()
|
|
bool deformationCourante=false; bool vitesseDeformationCourante=false;
|
|
bool almansi=false; bool greenLagrange=false;
|
|
bool logarithmique=false; bool deltaDef=false;
|
|
bool almansiTotal=false; bool greenLagrangeTotale=false;
|
|
bool logarithmiqueTotale=false; bool contrainteCourante=false;
|
|
bool defPrincipales=false; bool sigmaPrincipales=false;
|
|
bool vitPrincipales=false; bool contrainteMises=false;
|
|
// bool contraintesTresca=false; bool erreurQ=false;
|
|
// bool erreurRel = false;
|
|
bool defPlastiqueCumulee=false; bool def_duale_mises=false;
|
|
bool besoin_des_contraintes=false; bool besoin_des_deformation=false;
|
|
bool besoin_des_contraintes_barre=false; bool besoin_des_deformation_barre=false;
|
|
bool besoin_des_vitesses_deformation=false; bool besoin_des_vitesses_deformation_barre=false;
|
|
bool besoin_des_valpropre_sigma=false;
|
|
bool besoin_des_valpropre_deformation = false; bool besoin_des_valpropre_vitdef = false;
|
|
bool besoin_coordonnees = false;
|
|
bool besoin_coordonnees_t = false;bool besoin_coordonnees_t0 = false;
|
|
bool besoin_dir_princ_sig = false; bool besoin_dir_princ_eps = false;
|
|
bool besoin_dir_princ_D = false;
|
|
bool besoin_rep_local_ortho=false;
|
|
bool besoin_rep_giH = false; bool besoin_rep_giB = false;
|
|
bool def_SPHERIQUE_EPS = false; bool def_Q_EPS = false; bool def_COS3PHI_EPS = false;
|
|
bool def_SPHERIQUE_SIG = false; bool def_Q_SIG = false; bool def_COS3PHI_SIG = false;
|
|
bool def_SPHERIQUE_DEPS = false; bool def_Q_DEPS = false; bool def_COS3PHI_DEPS = false;
|
|
bool def_def_equivalente = false; bool def_duale_mises_maxi = false;
|
|
// --- dev d'un ensemble de variable booléenne pour gérer les sorties en une passe -----
|
|
// on se réfère au informations définit dans la méthode: Les_type_evolues_internes()
|
|
bool def_sig_mises= false; // *** peut-être en trop
|
|
bool def_sig_tresca= false; // *** peut-être en trop
|
|
|
|
|
|
// init pour l'utilisation de la liste d'exclusion
|
|
List_io<EnumTypeQuelconque>::const_iterator itt_deb;
|
|
List_io<EnumTypeQuelconque>::const_iterator itt_fin;
|
|
if (exclure_Q != NULL)
|
|
{ itt_deb = exclure_Q->begin();
|
|
itt_fin = exclure_Q->end();
|
|
};
|
|
|
|
// on initialise ces variables booléennes et les conteneurs
|
|
List_io<TypeQuelconque>::iterator ipq,ipqfin=enu.end();
|
|
for (ipq=enu.begin();ipq!=ipqfin;ipq++)
|
|
{EnumTypeQuelconque enuconq = (*ipq).EnuTypeQuelconque().EnumTQ();
|
|
switch (enuconq)
|
|
{ case CONTRAINTE_COURANTE : {contrainteCourante=true; besoin_des_contraintes=true;
|
|
Grandeur_TenseurHH& gr= *((Grandeur_TenseurHH*) ((*ipq).Grandeur_pointee()));
|
|
sigHH = gr.ConteneurTenseur();
|
|
|
|
break;}
|
|
case DEFORMATION_COURANTE : {deformationCourante=true; besoin_des_deformation=true;
|
|
Grandeur_TenseurBB& gr= *((Grandeur_TenseurBB*) ((*ipq).Grandeur_pointee()));
|
|
epsBB = gr.ConteneurTenseur(); break;}
|
|
case VITESSE_DEFORMATION_COURANTE : {vitesseDeformationCourante=true;
|
|
Grandeur_TenseurBB& gr= *((Grandeur_TenseurBB*) ((*ipq).Grandeur_pointee()));
|
|
DepsBB = gr.ConteneurTenseur(); besoin_des_vitesses_deformation=true; break;}
|
|
case ALMANSI : {almansi=true; besoin_des_deformation=true;
|
|
Grandeur_TenseurBB& gr= *((Grandeur_TenseurBB*) ((*ipq).Grandeur_pointee()));
|
|
epsAlmBB = gr.ConteneurTenseur(); break;}
|
|
case GREEN_LAGRANGE : {greenLagrange=true; besoin_des_deformation=true;
|
|
Grandeur_TenseurBB& gr= *((Grandeur_TenseurBB*) ((*ipq).Grandeur_pointee()));
|
|
eps0BB = gr.ConteneurTenseur(); break;}
|
|
case LOGARITHMIQUE : {logarithmique=true; besoin_des_deformation=true;
|
|
Grandeur_TenseurBB& gr= *((Grandeur_TenseurBB*) ((*ipq).Grandeur_pointee()));
|
|
epslogBB = gr.ConteneurTenseur(); break;}
|
|
case DELTA_DEF : {deltaDef=true; besoin_des_deformation=true;
|
|
Grandeur_TenseurBB& gr= *((Grandeur_TenseurBB*) ((*ipq).Grandeur_pointee()));
|
|
DeltaEpsBB = gr.ConteneurTenseur(); break;}
|
|
case ALMANSI_TOTAL : {almansiTotal=true; besoin_des_deformation=true;
|
|
Grandeur_TenseurBB& gr= *((Grandeur_TenseurBB*) ((*ipq).Grandeur_pointee()));
|
|
epsAlmTotalBB = gr.ConteneurTenseur(); break;}
|
|
case GREEN_LAGRANGE_TOTAL : {greenLagrangeTotale=true; besoin_des_deformation=true;
|
|
Grandeur_TenseurBB& gr= *((Grandeur_TenseurBB*) ((*ipq).Grandeur_pointee()));
|
|
epsGLTotalBB = gr.ConteneurTenseur(); break;}
|
|
case LOGARITHMIQUE_TOTALE : {logarithmiqueTotale=true; besoin_des_deformation=true;
|
|
Grandeur_TenseurBB& gr= *((Grandeur_TenseurBB*) ((*ipq).Grandeur_pointee()));
|
|
epsLogTotalBB = gr.ConteneurTenseur(); break;}
|
|
case DEF_PRINCIPALES : {defPrincipales=true; besoin_des_deformation=true;
|
|
besoin_des_valpropre_deformation=true;
|
|
Grandeur_coordonnee& gr= *((Grandeur_coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
valPropreEps = gr.ConteneurCoordonnee(); break;}
|
|
case SIGMA_PRINCIPALES : {sigmaPrincipales=true; besoin_des_contraintes=true;
|
|
besoin_des_valpropre_sigma=true;
|
|
Grandeur_coordonnee& gr= *((Grandeur_coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
valPropreSig = gr.ConteneurCoordonnee(); break;}
|
|
case VIT_PRINCIPALES : {vitPrincipales=true; besoin_des_vitesses_deformation=true;
|
|
besoin_des_valpropre_vitdef=true;
|
|
Grandeur_coordonnee& gr= *((Grandeur_coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
valPropreDeps = gr.ConteneurCoordonnee(); break;}
|
|
case DEF_DUALE_MISES : {def_duale_mises=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
defDualMises = gr.ConteneurDouble();
|
|
//besoin_des_valpropre_deformation=true; // non car maintenant on utilise directement ce qui est stocké au pt d'integ
|
|
break;}
|
|
case DEF_EQUIVALENTE : {def_def_equivalente=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
def_equivalente = gr.ConteneurDouble(); break;}
|
|
case DEF_DUALE_MISES_MAXI : {def_duale_mises_maxi=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
defDualMisesMaxi = gr.ConteneurDouble(); break;}
|
|
|
|
case CONTRAINTE_MISES : {def_sig_mises=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
sig_mises = gr.ConteneurDouble(); break;}
|
|
case CONTRAINTE_TRESCA : {def_sig_tresca=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
sig_tresca = gr.ConteneurDouble(); break;}
|
|
|
|
case POSITION_GEOMETRIQUE : {besoin_coordonnees=true;
|
|
Grandeur_coordonnee& gr= *((Grandeur_coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
Mtdt = gr.ConteneurCoordonnee(); break;}
|
|
case POSITION_GEOMETRIQUE_t : {besoin_coordonnees_t=true;
|
|
Grandeur_coordonnee& gr= *((Grandeur_coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
Mt = gr.ConteneurCoordonnee(); break;}
|
|
case POSITION_GEOMETRIQUE_t0 : {besoin_coordonnees_t0=true;
|
|
Grandeur_coordonnee& gr= *((Grandeur_coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
M0 = gr.ConteneurCoordonnee(); break;}
|
|
|
|
case SPHERIQUE_EPS : {def_SPHERIQUE_EPS=true; besoin_des_deformation=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
spherique_eps = gr.ConteneurDouble(); break;}
|
|
case Q_EPS : {def_Q_EPS=true; besoin_des_deformation=true;besoin_des_deformation_barre=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
Q_eps = gr.ConteneurDouble(); break;}
|
|
case COS3PHI_EPS : {def_COS3PHI_EPS=true; besoin_des_deformation=true;besoin_des_deformation_barre=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
cos3phi_eps = gr.ConteneurDouble(); besoin_des_valpropre_deformation=true; break;}
|
|
case SPHERIQUE_SIG : {def_SPHERIQUE_SIG=true; besoin_des_contraintes=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
spherique_sig = gr.ConteneurDouble(); besoin_des_valpropre_sigma=true; break;}
|
|
case Q_SIG : {def_Q_SIG=true; besoin_des_contraintes=true;besoin_des_contraintes_barre=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
Q_sig = gr.ConteneurDouble(); break;}
|
|
case COS3PHI_SIG : {def_COS3PHI_SIG=true; besoin_des_contraintes=true;besoin_des_contraintes_barre=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
cos3phi_sig = gr.ConteneurDouble(); break;}
|
|
case SPHERIQUE_DEPS : {def_SPHERIQUE_DEPS=true; besoin_des_vitesses_deformation=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
spherique_Deps = gr.ConteneurDouble(); break;}
|
|
case Q_DEPS : {def_Q_DEPS=true; besoin_des_vitesses_deformation=true;besoin_des_vitesses_deformation_barre=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
Q_Deps = gr.ConteneurDouble(); break;}
|
|
case COS3PHI_DEPS : {def_COS3PHI_DEPS=true; besoin_des_vitesses_deformation=true;besoin_des_vitesses_deformation_barre=true;
|
|
Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
cos3phi_Deps = gr.ConteneurDouble(); break;}
|
|
case REPERE_LOCAL_ORTHO : {besoin_rep_local_ortho=true;
|
|
Tab_Grandeur_Coordonnee& gr= *((Tab_Grandeur_Coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur REPERE_LOCAL_ORTHO necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
base_ad_hoc.Change_taille(dim_espace);
|
|
switch (dim_espace) {case 3: gr(3).Zero(); case 2: gr(2).Zero(); default:break;};//init
|
|
switch (dim_espace) {case 3: base_ad_hoc(3) = &(gr(3));
|
|
case 2: base_ad_hoc(2) = &(gr(2));
|
|
case 1: base_ad_hoc(1) = &(gr(1));
|
|
default:break;
|
|
};
|
|
break;}
|
|
case REPERE_LOCAL_H :
|
|
{besoin_rep_giH=true;
|
|
Tab_Grandeur_Coordonnee& gr= *((Tab_Grandeur_Coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur REPERE_LOCAL_H necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
base_giH.Change_taille(dim);
|
|
switch (dim_espace) {case 3: gr(3).Zero(); case 2: gr(2).Zero(); default:break;};//init
|
|
switch (dim) {case 3: base_giH(3) = &(gr(3));
|
|
case 2: base_giH(2) = &(gr(2));
|
|
case 1: base_giH(1) = &(gr(1));
|
|
default:break;
|
|
};
|
|
break;
|
|
}
|
|
case REPERE_LOCAL_B :
|
|
{besoin_rep_giB=true;
|
|
Tab_Grandeur_Coordonnee& gr= *((Tab_Grandeur_Coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur REPERE_LOCAL_B necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
base_giB.Change_taille(dim);
|
|
switch (dim_espace) {case 3: gr(3).Zero(); case 2: gr(2).Zero(); default:break;};//init
|
|
switch (dim) {case 3: base_giB(3) = &(gr(3));
|
|
case 2: base_giB(2) = &(gr(2));
|
|
case 1: base_giB(1) = &(gr(1));
|
|
default:break;
|
|
};
|
|
break;
|
|
}
|
|
case DIRECTIONS_PRINC_SIGMA : {besoin_des_contraintes=true;
|
|
besoin_des_valpropre_sigma=true;besoin_dir_princ_sig=true;
|
|
Tab_Grandeur_Coordonnee& gr= *((Tab_Grandeur_Coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur DIRECTIONS_PRINC_SIGMA necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
switch (dim_espace) {case 3: gr(3).Zero(); case 2: gr(2).Zero(); default:break;};//init
|
|
base_propre_sigma.Change_taille(dim);
|
|
switch (dim) {case 3: base_propre_sigma(3) = &(gr(3));
|
|
case 2: base_propre_sigma(2) = &(gr(2));
|
|
case 1: base_propre_sigma(1) = &(gr(1));
|
|
default:break;
|
|
};
|
|
break;}
|
|
case DIRECTIONS_PRINC_DEF : {besoin_des_deformation=true;
|
|
besoin_des_valpropre_deformation=true;besoin_dir_princ_eps=true;
|
|
Tab_Grandeur_Coordonnee& gr= *((Tab_Grandeur_Coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur DIRECTIONS_PRINC_DEF necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
switch (dim_espace) {case 3: gr(3).Zero(); case 2: gr(2).Zero(); default:break;};//init
|
|
base_propre_eps.Change_taille(dim);
|
|
switch (dim) {case 3: base_propre_eps(3) = &(gr(3));
|
|
case 2: base_propre_eps(2) = &(gr(2));
|
|
case 1: base_propre_eps(1) = &(gr(1));
|
|
default:break;
|
|
};
|
|
break;}
|
|
case DIRECTIONS_PRINC_D : {vitesseDeformationCourante=true;besoin_des_vitesses_deformation=true;
|
|
besoin_des_valpropre_deformation=true;besoin_dir_princ_D=true;
|
|
Tab_Grandeur_Coordonnee& gr= *((Tab_Grandeur_Coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur DIRECTIONS_PRINC_D necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
switch (dim_espace) {case 3: gr(3).Zero(); case 2: gr(2).Zero(); default:break;};//init
|
|
base_propre_D.Change_taille(dim);
|
|
switch (dim) {case 3: base_propre_D(3) = &(gr(3));
|
|
case 2: base_propre_D(2) = &(gr(2));
|
|
case 1: base_propre_D(1) = &(gr(1));
|
|
default:break;
|
|
};
|
|
break;}
|
|
case NN_SURF:{
|
|
Grandeur_coordonnee& gr= *((Grandeur_coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
N_surf = gr.ConteneurCoordonnee(); break;}
|
|
case NN_SURF_t:{
|
|
Grandeur_coordonnee& gr= *((Grandeur_coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
N_surf_t = gr.ConteneurCoordonnee(); break;}
|
|
case NN_SURF_t0:{
|
|
Grandeur_coordonnee& gr= *((Grandeur_coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
N_surf_t0 = gr.ConteneurCoordonnee(); break;}
|
|
case DEPLACEMENT:{besoin_coordonnees=true;
|
|
Grandeur_coordonnee& gr= *((Grandeur_coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
Deplacement = gr.ConteneurCoordonnee(); break;}
|
|
case VITESSE:{
|
|
Grandeur_coordonnee& gr= *((Grandeur_coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
Vitesse = gr.ConteneurCoordonnee(); break;}
|
|
|
|
// dans le cas des numéros, traitement direct ici
|
|
case NUM_ELEMENT:
|
|
{if (ptintmeca_en_cours != NULL)
|
|
{*((Grandeur_scalaire_entier*) ((*ipq).Grandeur_pointee()))= ptintmeca_en_cours->Nb_ele();}
|
|
// sinon on le laisse à 0
|
|
break;
|
|
}
|
|
case NUM_MAIL_ELEM:
|
|
{ if (ptintmeca_en_cours != NULL)
|
|
*((Grandeur_scalaire_entier*) ((*ipq).Grandeur_pointee()))= ptintmeca_en_cours->Nb_mail();
|
|
break;
|
|
}
|
|
case NUM_PTI:
|
|
{ if (ptintmeca_en_cours != NULL)
|
|
*((Grandeur_scalaire_entier*) ((*ipq).Grandeur_pointee()))= ptintmeca_en_cours->Nb_pti();
|
|
break;
|
|
}
|
|
|
|
default :
|
|
{ // on regarde si la grandeur en fait n'est pas à calculer
|
|
bool a_atraiter = true;
|
|
if (exclure_Q != NULL)
|
|
if (find(itt_deb,itt_fin,enuconq) != itt_fin)
|
|
a_atraiter = false;
|
|
if (a_atraiter)
|
|
// cas où ce n'est pas à exclure, donc cela manque
|
|
{// on initialise la grandeur pour éviter d'avoir des valeurs aléatoires
|
|
((*ipq).Grandeur_pointee())->InitParDefaut();
|
|
if (ParaGlob::NiveauImpression() > 0)
|
|
{cout << "\nWarning : attention cas non traite: "
|
|
<< (*ipq).EnuTypeQuelconque().NomPlein() << "!\n";
|
|
if (ParaGlob::NiveauImpression() > 5)
|
|
cout << "\n Loi_comp_abstraite::Valeurs_Tensorielles_interpoler_ou_calculer(....";
|
|
};
|
|
}; // sinon on ne fait rien, car les grandeurs exclues sont sensées
|
|
// être calculés par ailleurs
|
|
}
|
|
};
|
|
};
|
|
|
|
// on complète les définitions de tenseurs si besoin
|
|
// les tenseurs restants en locale
|
|
TenseurHB* sigHB = NULL ;TenseurHB* sig_barreHB = NULL ;
|
|
TenseurHB* epsHB = NULL ;TenseurHB* eps_barreHB = NULL ;
|
|
TenseurHB* DepsHB = NULL ; TenseurHB* Deps_barreHB = NULL ;
|
|
if ((besoin_des_contraintes && !contrainteCourante)
|
|
|| (besoin_des_valpropre_sigma && !sigmaPrincipales)
|
|
)
|
|
{sigHH = NevezTenseurHH(dim_sortie_tenseur) ;
|
|
sigHB = (NevezTenseurHB(dim)) ;
|
|
sig_barreHB = (NevezTenseurHB(dim)) ;
|
|
}
|
|
else if (besoin_des_contraintes
|
|
|| (besoin_des_valpropre_sigma && !sigmaPrincipales)
|
|
)
|
|
// là il s'agit uniquement des tenseurs locaux
|
|
{sigHB = (NevezTenseurHB(dim)) ;
|
|
sig_barreHB = (NevezTenseurHB(dim)) ;
|
|
};
|
|
if ((besoin_des_deformation && !deformationCourante)
|
|
|| (besoin_des_valpropre_deformation && !defPrincipales)
|
|
)
|
|
{epsBB = NevezTenseurBB(dim_sortie_tenseur) ;
|
|
epsHB = (NevezTenseurHB(dim)) ;
|
|
eps_barreHB = (NevezTenseurHB(dim)) ;
|
|
}
|
|
else if (besoin_des_deformation
|
|
|| (besoin_des_valpropre_deformation && !defPrincipales)
|
|
)
|
|
// là il s'agit uniquement des tenseurs locaux
|
|
{epsHB = (NevezTenseurHB(dim)) ;
|
|
eps_barreHB = (NevezTenseurHB(dim)) ;
|
|
};
|
|
if ((besoin_des_vitesses_deformation && !vitesseDeformationCourante)
|
|
|| (besoin_des_valpropre_vitdef && !vitPrincipales)
|
|
)
|
|
{DepsBB = NevezTenseurBB(dim_sortie_tenseur);
|
|
DepsHB = (NevezTenseurHB(dim));
|
|
Deps_barreHB = (NevezTenseurHB(dim)) ;
|
|
}
|
|
else if(besoin_des_vitesses_deformation
|
|
|| (besoin_des_valpropre_vitdef && !vitPrincipales)
|
|
)
|
|
// là il s'agit uniquement des tenseurs locaux
|
|
{DepsHB = (NevezTenseurHB(dim));
|
|
Deps_barreHB = (NevezTenseurHB(dim)) ;
|
|
};
|
|
if (besoin_des_valpropre_deformation && !defPrincipales) valPropreEps = new Coordonnee(dim_sortie_tenseur);
|
|
if (besoin_des_valpropre_vitdef && !vitPrincipales) valPropreDeps = new Coordonnee(dim_sortie_tenseur);
|
|
if (besoin_des_valpropre_sigma && !sigmaPrincipales) valPropreSig = new Coordonnee(dim_sortie_tenseur);
|
|
|
|
// on statut sur le fait d'avoir besoin ou non des chgt de base
|
|
bool besoin_matrice_chg_base = false;
|
|
if ( besoin_des_contraintes
|
|
|| besoin_des_deformation
|
|
|| besoin_des_vitesses_deformation
|
|
|| besoin_rep_local_ortho
|
|
)
|
|
{besoin_matrice_chg_base = true;};
|
|
|
|
// on ne change pas le numéro de point d'intégration courant
|
|
// on considère ici que c'est déjà le bon, puisque c'est appelé par un élément
|
|
// a priori ...
|
|
|
|
// matrices de passage
|
|
int dim_effective = dim; // init
|
|
if (absolue) dim_effective = ParaGlob::Dimension();
|
|
Mat_pleine* Aa0 = NULL;Mat_pleine* Aafin = NULL;
|
|
Mat_pleine* gamma0 = NULL;Mat_pleine* gammafin = NULL;
|
|
Mat_pleine* beta0 = NULL;Mat_pleine* betafin = NULL;
|
|
if (besoin_matrice_chg_base)
|
|
// dans le cas où on n'est pas en absolue => on sort dans un repère ad hoc donc
|
|
// il a la dimension locale
|
|
// sinon on sort dans le repère globale => il a la dimension globale
|
|
{Aa0 = new Mat_pleine(dim_effective,dim_effective);
|
|
Aafin = new Mat_pleine(dim_effective,dim_effective);
|
|
gamma0 = new Mat_pleine(dim_effective,dim_effective);
|
|
gammafin = new Mat_pleine(dim_effective,dim_effective);
|
|
beta0 = new Mat_pleine(dim_effective,dim_effective);
|
|
betafin = new Mat_pleine(dim_effective,dim_effective);
|
|
};
|
|
// on considère que les métriques sont directement utilisables
|
|
// si elles sont disponibles
|
|
if (besoin_matrice_chg_base)
|
|
{if (pas_de_metrique_dispo)
|
|
{cout << "\n *** erreur : on a besoin de matrices de changement de base et il n'y a pas "
|
|
<< " de metrique disponible: impossible de continuer"
|
|
<< "\n Loi_comp_abstraite::Valeurs_Tensorielles_interpoler_ou_calculer..." << endl;
|
|
Sortie(1);
|
|
}
|
|
else if (def_en_cours== NULL)
|
|
{cout << "\n *** erreur : on a besoin de l'objet Deformation et il n'y a pas "
|
|
<< " de pointeur de deformation disponible: impossible de continuer"
|
|
<< "\n Loi_comp_abstraite::Valeurs_Tensorielles_interpoler_ou_calculer..." << endl;
|
|
Sortie(1);
|
|
}
|
|
else
|
|
// on peut calculer
|
|
{Mat_pleine Aat(dim_effective,dim_effective);
|
|
// a priori Aat ne sert pas par la suite, mais est nécessaire pour le passage de par
|
|
const Met_abstraite::Info_et_metrique_0_t_tdt ex
|
|
= def_en_cours->Remont_et_metrique_0_t_tdtSansCalMet(absolue,*Aa0,Aat,*Aafin);
|
|
// pour les formules de passage de repère il nous faut :
|
|
// Ip_a = beta_a^{.j} g_j et Ip^b = gamma^b_{.j} g^j
|
|
// on a: [beta_a^{.j}] = [Aa^j_{.a}]^T
|
|
// et [gamma^b_{.j}] = [beta_a^{.j}]^{-1T} = [Aa^j_{.a}]^{-1}
|
|
(*gamma0) = (Aa0->Inverse());
|
|
(*gammafin) = (Aafin->Inverse());
|
|
// on détermine également les matrices beta
|
|
(*beta0) = (Aa0->Transpose());
|
|
(*betafin) = (Aafin->Transpose());
|
|
};
|
|
};
|
|
|
|
|
|
// récup des bases si besoin
|
|
if (besoin_rep_local_ortho)
|
|
{if ((!absolue)&&(dim_espace==3)&&(dim==2))
|
|
// cas d'éléments 2D, pour lesquels on veut un repère local ad hoc
|
|
// on ramène une base à 3 vecteurs
|
|
{ *(base_ad_hoc(1)) = jBfin(1,1) * giB->Coordo(1) + jBfin(2,1) * giB->Coordo(2);
|
|
*(base_ad_hoc(2)) = jBfin(1,2) * giB->Coordo(1) + jBfin(2,2) * giB->Coordo(2);
|
|
*(base_ad_hoc(3)) = Util::ProdVec_coor(*(base_ad_hoc(1)),*(base_ad_hoc(2)));
|
|
}
|
|
else if((!absolue)&&(dim_espace>1)&&(dim==1))
|
|
// cas d'éléments 1D, dans un espace 2D ou 3D
|
|
// on ramène un seul vecteur non nul, les autres ne peuvent être calculé sans info supplémentaire
|
|
{ *(base_ad_hoc(1)) = jBfin(1,1) * giB->Coordo(1);
|
|
(base_ad_hoc(2))->Zero(); (base_ad_hoc(3))->Zero(); // init à 0 par défaut
|
|
}
|
|
else // dans tous les autres cas
|
|
{ switch (dim_espace) // on se contente de ramener le repère identité
|
|
{case 3: (base_ad_hoc(3))->Zero();(*(base_ad_hoc(3)))(3)=1.;
|
|
case 2: (base_ad_hoc(2))->Zero();(*(base_ad_hoc(2)))(2)=1.;
|
|
case 1: (base_ad_hoc(1))->Zero();(*(base_ad_hoc(1)))(1)=1.;
|
|
default:break;
|
|
};
|
|
};
|
|
};
|
|
|
|
if (besoin_rep_giH)
|
|
{switch (dim) {case 3: *(base_giH(3)) = giH->Coordo(3);
|
|
case 2: *(base_giH(2)) = giH->Coordo(2);
|
|
case 1: *(base_giH(1)) = giH->Coordo(1);
|
|
default:break;
|
|
};
|
|
};
|
|
if (besoin_rep_giB)
|
|
{switch (dim) {case 3: *(base_giB(3)) = giB->Coordo(3);
|
|
case 2: *(base_giB(2)) = giB->Coordo(2);
|
|
case 1: *(base_giB(1)) = giB->Coordo(1);
|
|
default:break;
|
|
};
|
|
};
|
|
|
|
// ----- calcul des grandeurs à sortir
|
|
// calcul des tenseurs initiaux
|
|
bool plusZero = true; // s'il faut rajouter des termes, on met des 0
|
|
if (besoin_des_contraintes)
|
|
{(*sigHB) = (ptintmeca_en_cours->SigHH_const()) * (*gijBB);
|
|
if (contrainteCourante) // on n'intervient ici que si on veut une sortie des contraintes courantes
|
|
{if (absolue) {(ptintmeca_en_cours->SigHH_const()).BaseAbsolue(*sigHH,*giB);}// changement de base finale
|
|
else if (transfert_tenseur)
|
|
{ TenseurHH* sigHH_inter = NevezTenseurHH(dim) ;
|
|
*sigHH_inter = (ptintmeca_en_cours->SigHH_const()); sigHH_inter->ChBase(*gammafin);
|
|
sigHH->Affectation_trans_dimension(*sigHH_inter,false);
|
|
delete sigHH_inter;
|
|
}
|
|
else
|
|
{ *sigHH = (ptintmeca_en_cours->SigHH_const());sigHH->ChBase(*gammafin);};
|
|
};
|
|
};
|
|
|
|
if (besoin_des_deformation)
|
|
{// cas de delta_eps
|
|
if(DeltaEpsBB != NULL)
|
|
{if (absolue)// changement de base finale
|
|
{(ptintmeca_en_cours->DeltaEpsBB_const()).BaseAbsolue(*DeltaEpsBB,*giH);}
|
|
else if (transfert_tenseur)
|
|
{ TenseurBB* DeltaEpsBB_inter = NevezTenseurBB(dim) ;
|
|
*DeltaEpsBB_inter = (ptintmeca_en_cours->DeltaEpsBB_const()); DeltaEpsBB_inter->ChBase(*betafin);
|
|
DeltaEpsBB->Affectation_trans_dimension(*DeltaEpsBB_inter,false);
|
|
delete DeltaEpsBB_inter;
|
|
}
|
|
else {*DeltaEpsBB = (ptintmeca_en_cours->DeltaEpsBB_const());DeltaEpsBB->ChBase(*betafin);};
|
|
};
|
|
// cas de la déformation
|
|
(*epsHB) = (*gijHH) * ((ptintmeca_en_cours->EpsBB_const()));
|
|
if (deformationCourante)// on n'intervient ici que si on veut une sortie des déformations courantes
|
|
{if (absolue)// changement de base finale
|
|
{(ptintmeca_en_cours->EpsBB_const()).BaseAbsolue(*epsBB,*giH);}
|
|
else if (transfert_tenseur)
|
|
{ TenseurBB* epsBB_inter = NevezTenseurBB(dim) ;
|
|
*epsBB_inter = (ptintmeca_en_cours->EpsBB_const()); epsBB_inter->ChBase(*betafin);
|
|
epsBB->Affectation_trans_dimension(*epsBB_inter,false);
|
|
delete epsBB_inter;
|
|
}
|
|
else {*epsBB = (ptintmeca_en_cours->EpsBB_const());epsBB->ChBase(*betafin);};
|
|
};
|
|
switch (def_en_cours->Type_de_deformation())
|
|
{case DEFORMATION_STANDART : // c'est à dire almansi
|
|
{if (greenLagrange)
|
|
{if (absolue)
|
|
{(ptintmeca_en_cours->EpsBB_const()).BaseAbsolue(*eps0BB,*giH_0);}// changement de base finale
|
|
else if (transfert_tenseur)
|
|
{ TenseurBB* eps0BB_inter = NevezTenseurBB(dim) ;
|
|
*eps0BB_inter = (ptintmeca_en_cours->EpsBB_const()); eps0BB_inter->ChBase(*beta0);
|
|
eps0BB->Affectation_trans_dimension(*eps0BB_inter,false);
|
|
delete eps0BB_inter;
|
|
}
|
|
else {eps0BB->ChBase(*beta0);};
|
|
};
|
|
if (almansi) *epsAlmBB = *epsBB;// le changement de base a été fait juste plus haut
|
|
if (almansiTotal) // cas avec dilatation et demande de def Almansi totale
|
|
{TenseurBB* epsAlmTotal_local_BB = epsAlmTotalBB; // par défaut
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur)
|
|
epsAlmTotal_local_BB = NevezTenseurBB(dim);
|
|
def_en_cours->Cal_deformation (temps,*epsAlmTotal_local_BB);
|
|
if (absolue)// changement de base finale
|
|
{epsAlmTotal_local_BB->BaseAbsolue(*epsAlmTotalBB,*giH);}
|
|
else if (transfert_tenseur)
|
|
{ epsAlmTotal_local_BB->ChBase(*betafin);
|
|
epsAlmTotalBB->Affectation_trans_dimension(*epsAlmTotal_local_BB,false);
|
|
}
|
|
else {epsAlmTotalBB->ChBase(*betafin);}; // ici epsAlmTotal_local_BB == epsAlmTotalBB
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur) delete epsAlmTotal_local_BB; // car pas utilisé ensuite
|
|
};
|
|
if (greenLagrangeTotale) // cas avec dilatation et demande de def Green_Lagrange totale
|
|
{TenseurBB* epsGLTotal_local_BB = epsGLTotalBB; // par défaut
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur)
|
|
epsGLTotal_local_BB = NevezTenseurBB(dim);
|
|
def_en_cours->Cal_deformation (temps,*epsGLTotal_local_BB);
|
|
if (absolue)// changement de base finale
|
|
{epsGLTotal_local_BB->BaseAbsolue(*epsGLTotalBB,*giH_0);}
|
|
else if (transfert_tenseur)
|
|
{ epsGLTotal_local_BB->ChBase(*beta0);
|
|
epsGLTotalBB->Affectation_trans_dimension(*epsGLTotal_local_BB,false);
|
|
}
|
|
else {epsGLTotalBB->ChBase(*beta0);}; // ici epsGLTotal_local_BB == epsGLTotalBB
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur) delete epsGLTotal_local_BB; // car pas utilisé ensuite
|
|
};
|
|
// si l'on veut sortir la déformation logarithmique le plus simple est de la calculer
|
|
if (logarithmiqueTotale || logarithmique)
|
|
{def_en_cours->Change_type_de_deformation(DEFORMATION_LOGARITHMIQUE);
|
|
if (logarithmique) // cas du calcul de la def logarithmique
|
|
{TenseurBB* epslog_local_BB = epslogBB; // par défaut
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur)
|
|
epslog_local_BB = NevezTenseurBB(dim);
|
|
def_en_cours->Cal_deformation (temps,*epslog_local_BB);
|
|
if (absolue)// changement de base finale
|
|
{epslog_local_BB->BaseAbsolue(*epslogBB,*giH);}
|
|
else if (transfert_tenseur)
|
|
{ epslog_local_BB->ChBase(*betafin);
|
|
epslogBB->Affectation_trans_dimension(*epslog_local_BB,false);
|
|
}
|
|
else {epslogBB->ChBase(*betafin);}; // ici epslog_local_BB == epslogBB
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur) delete epslog_local_BB; // car pas utilisé ensuite
|
|
};
|
|
if (logarithmiqueTotale) // cas avec dilatation et demande de def log totale
|
|
{TenseurBB* epsLogTotal_local_BB = epsLogTotalBB; // par défaut
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur)
|
|
epsLogTotal_local_BB = NevezTenseurBB(dim);
|
|
def_en_cours->Cal_deformation (temps,*epsLogTotal_local_BB);
|
|
if (absolue)// changement de base finale
|
|
{epsLogTotal_local_BB->BaseAbsolue(*epsLogTotalBB,*giH);}
|
|
else if (transfert_tenseur)
|
|
{ epsLogTotal_local_BB->ChBase(*betafin);
|
|
epsLogTotalBB->Affectation_trans_dimension(*epsLogTotal_local_BB,false);
|
|
}
|
|
else {epsLogTotalBB->ChBase(*betafin);}; // ici epsLogTotal_local_BB == epsLogTotalBB
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur) delete epsLogTotal_local_BB; // car pas utilisé ensuite
|
|
};
|
|
def_en_cours->Change_type_de_deformation(DEFORMATION_STANDART); // on revient au type initial
|
|
};
|
|
break;
|
|
}
|
|
case DEFORMATION_LOGARITHMIQUE :
|
|
{ if (logarithmique) *epslogBB=*epsBB;
|
|
if (logarithmiqueTotale) // cas avec dilatation et demande de def log totale
|
|
{TenseurBB* epsLogTotal_local_BB = epsLogTotalBB; // par défaut
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur)
|
|
epsLogTotal_local_BB = NevezTenseurBB(dim);
|
|
def_en_cours->Cal_deformation (temps,*epsLogTotal_local_BB);
|
|
if (absolue)// changement de base finale
|
|
{epsLogTotal_local_BB->BaseAbsolue(*epsLogTotalBB,*giH);}
|
|
else if (transfert_tenseur)
|
|
{ epsLogTotal_local_BB->ChBase(*betafin);
|
|
epsLogTotalBB->Affectation_trans_dimension(*epsLogTotal_local_BB,false);
|
|
}
|
|
else {epsLogTotalBB->ChBase(*betafin);}; // ici epsLogTotal_local_BB == epsLogTotalBB
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur) delete epsLogTotal_local_BB; // car pas utilisé ensuite
|
|
};
|
|
// si l'on veut sortir la déformation d'Almansi ou de green-lagrange le plus simple est de les calculer
|
|
if (almansi || greenLagrangeTotale || almansiTotal)
|
|
{def_en_cours->Change_type_de_deformation(DEFORMATION_STANDART);
|
|
if (almansi) // cas de la def d'almansi
|
|
{ TenseurBB* eps_local_BB = epsAlmBB; // par défaut
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur)
|
|
eps_local_BB = NevezTenseurBB(dim);
|
|
def_en_cours->Cal_deformation (temps,*eps_local_BB);
|
|
if (absolue)// changement de base finale
|
|
{eps_local_BB->BaseAbsolue(*epsAlmBB,*giH);}
|
|
else if (transfert_tenseur)
|
|
{ eps_local_BB->ChBase(*betafin);
|
|
epsAlmBB->Affectation_trans_dimension(*eps_local_BB,false);
|
|
}
|
|
else {epsAlmBB->ChBase(*betafin);};// ici eps_local_BB == epsAlmBB
|
|
if(greenLagrange)
|
|
{if (absolue)// changement de base finale
|
|
{eps_local_BB->BaseAbsolue(*eps0BB,*giH_0);}
|
|
else if (transfert_tenseur)
|
|
{ eps_local_BB->ChBase(*beta0);
|
|
eps0BB->Affectation_trans_dimension(*eps_local_BB,false);
|
|
}
|
|
else {eps0BB->ChBase(*beta0);}; // ici eps_local_BB == eps0BB
|
|
};
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur) delete eps_local_BB; // car pas utilisé ensuite
|
|
};
|
|
if (almansiTotal) // cas avec dilatation et demande de def Almansi totale
|
|
{TenseurBB* epsAlmTotal_local_BB = epsAlmTotalBB; // par défaut
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur)
|
|
epsAlmTotal_local_BB = NevezTenseurBB(dim);
|
|
def_en_cours->Cal_deformation (temps,*epsAlmTotal_local_BB);
|
|
if (absolue)// changement de base finale
|
|
{epsAlmTotal_local_BB->BaseAbsolue(*epsAlmTotalBB,*giH);}
|
|
else if (transfert_tenseur)
|
|
{ epsAlmTotal_local_BB->ChBase(*betafin);
|
|
epsAlmTotalBB->Affectation_trans_dimension(*epsAlmTotal_local_BB,false);
|
|
}
|
|
else {epsAlmTotalBB->ChBase(*betafin);}; // ici epsAlmTotal_local_BB == epsAlmTotalBB
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur) delete epsAlmTotal_local_BB; // car pas utilisé ensuite
|
|
};
|
|
if (greenLagrangeTotale) // cas avec dilatation et demande de def Green_Lagrange totale
|
|
{TenseurBB* epsGLTotal_local_BB = epsGLTotalBB; // par défaut
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur)
|
|
epsGLTotal_local_BB = NevezTenseurBB(dim);
|
|
def_en_cours->Cal_deformation (temps,*epsGLTotal_local_BB);
|
|
if (absolue)// changement de base finale
|
|
{epsGLTotal_local_BB->BaseAbsolue(*epsGLTotalBB,*giH_0);}
|
|
else if (transfert_tenseur)
|
|
{ epsGLTotal_local_BB->ChBase(*beta0);
|
|
epsGLTotalBB->Affectation_trans_dimension(*epsGLTotal_local_BB,false);
|
|
}
|
|
else {epsGLTotalBB->ChBase(*beta0);}; // ici epsGLTotal_local_BB == epsGLTotalBB
|
|
if ((prevoir_change_dim_tenseur)|| transfert_tenseur) delete epsGLTotal_local_BB; // car pas utilisé ensuite
|
|
};
|
|
def_en_cours->Change_type_de_deformation(DEFORMATION_LOGARITHMIQUE); // on revient au type initial
|
|
};
|
|
break;
|
|
}
|
|
default:
|
|
cout << "\n cas de deformation non encore implante en sortie de visualisation "
|
|
<< Nom_type_deformation(def_en_cours->Type_de_deformation())
|
|
<< " affichage donc errone des valeurs !!!";
|
|
};
|
|
}; //-- fin de if (besoin_des_deformation)
|
|
if (besoin_des_vitesses_deformation)
|
|
{ *DepsHB = (*gijHH) * ((ptintmeca_en_cours->DepsBB_const()));
|
|
if (absolue)// changement de base finale
|
|
{(ptintmeca_en_cours->DepsBB_const()).BaseAbsolue(*DepsBB,*giH);}
|
|
else if (transfert_tenseur)
|
|
{ TenseurBB* DepsBB_inter = NevezTenseurBB(dim) ;
|
|
*DepsBB_inter = (ptintmeca_en_cours->DepsBB_const()); DepsBB_inter->ChBase(*betafin);
|
|
DepsBB->Affectation_trans_dimension(*DepsBB_inter,false);
|
|
delete DepsBB_inter;
|
|
}
|
|
else {*DepsBB = (ptintmeca_en_cours->DepsBB_const());DepsBB->ChBase(*betafin);};
|
|
};
|
|
|
|
if (besoin_des_contraintes_barre)
|
|
{double Isig = sigHB->Trace(); // trace de la déformation
|
|
*sig_barreHB = (*sigHB) - (Isig/dim_espace) * (*Id_dim_HB(dim));
|
|
};
|
|
if (besoin_des_deformation_barre)
|
|
{double Ieps = epsHB->Trace(); // trace de la déformation
|
|
*eps_barreHB = (*epsHB) - (Ieps/dim_espace) * (*Id_dim_HB(dim));
|
|
};
|
|
if (besoin_des_vitesses_deformation_barre)
|
|
{double IDeps = DepsHB->Trace(); // trace de la déformation
|
|
*Deps_barreHB = (*DepsHB) - (IDeps/dim_espace) * (*Id_dim_HB(dim));
|
|
};
|
|
|
|
|
|
// cas des valeurs propres et éventuellement des vecteurs propres
|
|
{int caas=0;
|
|
////----- debug
|
|
//cout << "\n besoin_des_valpropre_sigma= "<< besoin_des_valpropre_sigma
|
|
// << " besoin_dir_princ_sig= "<< besoin_dir_princ_sig << endl;
|
|
////--- fin debug
|
|
if (besoin_des_valpropre_sigma && besoin_dir_princ_sig)// on veut les directions et les valeurs propres
|
|
{ Mat_pleine mat(dim,dim); // contiendra par colonne les vecteurs principaux, exprimé en giH
|
|
Coordonnee inter(sigHB->ValPropre(caas,mat));
|
|
inter.Change_dim(dim_sortie_tenseur); // on étant la taille éventuellement
|
|
*valPropreSig = inter; // sauvegarde des valeurs propres
|
|
// puis des directions principales, que l'on doit exprimer dans le repère absolue
|
|
Tableau <CoordonneeH > tab = mat.CoordonneeH_Base_associee(); // récup en tab de coor
|
|
// on regarde le cas particulier ou les valeurs propres sont toutes nulles
|
|
// si c'est le cas, on ne fait rien, en sortie on aura des vecteurs propres nulles
|
|
if (inter.Max_val_abs() > ConstMath::petit)
|
|
// et s'il y a eu un pb dans le calcul des valeurs propres ou vecteurs propres on évite
|
|
{if (caas != -1)
|
|
{switch (dim)
|
|
{case 3: giB->BaseAbsolue( *(base_propre_sigma(3)),tab(3));(base_propre_sigma(3))->Normer();
|
|
giB->BaseAbsolue( *(base_propre_sigma(2)),tab(2));(base_propre_sigma(2))->Normer();
|
|
case 1: giB->BaseAbsolue( *(base_propre_sigma(1)),tab(1));(base_propre_sigma(1))->Normer();
|
|
break;
|
|
case 2: // en 2D le premier vecteur en giB et le second en giH !!
|
|
giB->BaseAbsolue( *(base_propre_sigma(1)),tab(1));(base_propre_sigma(1))->Normer();
|
|
giH->BaseAbsolue( *(base_propre_sigma(2)),mat.CoordonneeB_Base_associee(2));
|
|
(base_propre_sigma(2))->Normer();
|
|
break;
|
|
default:break;
|
|
};
|
|
};
|
|
};
|
|
}
|
|
else if (besoin_dir_princ_sig) // cas où on ne veut que les directions principales
|
|
{ Mat_pleine mat(dim,dim); // contiendra par colonne les vecteurs principaux, exprimé en giH
|
|
Coordonnee inter(sigHB->ValPropre(caas,mat));
|
|
// sauvegarde des directions principales
|
|
Tableau <CoordonneeH > tab = mat.CoordonneeH_Base_associee(); // récup en tab de coor
|
|
// on regarde le cas particulier ou les valeurs propres sont toutes nulles
|
|
// si c'est le cas, on ne fait rien, en sortie on aura des vecteurs propres nulles
|
|
if (inter.Max_val_abs() > ConstMath::petit)
|
|
// et s'il y a eu un pb dans le calcul des valeurs propres ou vecteurs propres on évite
|
|
{if (caas != -1)
|
|
{switch (dim)
|
|
{case 3: giB->BaseAbsolue( *(base_propre_sigma(3)),tab(3));(base_propre_sigma(3))->Normer();
|
|
giB->BaseAbsolue( *(base_propre_sigma(2)),tab(2));(base_propre_sigma(2))->Normer();
|
|
case 1: giB->BaseAbsolue( *(base_propre_sigma(1)),tab(1));(base_propre_sigma(1))->Normer();
|
|
break;
|
|
case 2: // en 2D le premier vecteur en en giB et le second en giH !!
|
|
giB->BaseAbsolue( *(base_propre_sigma(1)),tab(1));(base_propre_sigma(1))->Normer();
|
|
giH->BaseAbsolue( *(base_propre_sigma(2)),mat.CoordonneeB_Base_associee(2));
|
|
(base_propre_sigma(2))->Normer();
|
|
break;
|
|
default:break;
|
|
};
|
|
};
|
|
};
|
|
}
|
|
else if (besoin_des_valpropre_sigma)// on ne veut que les valeurs propres
|
|
{ Coordonnee inter(sigHB->ValPropre(caas));
|
|
inter.Change_dim(dim_sortie_tenseur); // on étend la taille éventuellement
|
|
*valPropreSig = inter; // sauvegarde des valeurs propres
|
|
};
|
|
// gestion d'une erreur éventuelle
|
|
if (caas == -1)
|
|
{ cout << "\n warning *** erreur dans le calcul des valeurs propres et-ou vecteurs propres de la contrainte ";
|
|
if (ParaGlob::NiveauImpression() > 5) {sigHB->Ecriture(cout);cout << "\n cas = "<< caas ;
|
|
cout << "\Loi_comp_abstraite::Valeurs_Tensorielles_interpoler_ou_calculer(...";};
|
|
cout << endl;
|
|
};
|
|
}; // -- fin de l'encapsulation du cas des contraintes
|
|
|
|
{int caas=0;
|
|
if (besoin_des_valpropre_deformation && besoin_dir_princ_eps)// on veut les directions et les valeurs propres
|
|
{ Mat_pleine mat(dim,dim); // contiendra par colonne les vecteurs principaux, exprimé en giH
|
|
// 1) calcul des valeurs propres dans un vecteur de travail inter, et des vecteurs propres stockés
|
|
Coordonnee inter(epsHB->ValPropre(caas,mat)); // dans la matrice mat
|
|
inter.Change_dim(dim_sortie_tenseur); // on étend la taille, dans le cas ou le nb de valeurs
|
|
// propre est inférieur à la dimension de l'espace
|
|
*valPropreEps = inter; // sauvegarde des valeurs propres
|
|
|
|
// 2) puis des directions principales, que l'on doit exprimer dans le repère absolue
|
|
Tableau <CoordonneeH > tab = mat.CoordonneeH_Base_associee(); // récup en tab de coor
|
|
// on regarde le cas particulier ou les valeurs propres sont toutes nulles
|
|
// si c'est le cas, on ne fait rien, en sortie on aura des vecteurs propres nulles
|
|
if (inter.Max_val_abs() > ConstMath::petit)
|
|
// et s'il y a eu un pb dans le calcul des valeurs propres ou vecteurs propres on évite
|
|
{if (caas != -1)
|
|
{switch (dim)
|
|
{case 3: giB->BaseAbsolue( *(base_propre_eps(3)),tab(3));(base_propre_eps(3))->Normer();
|
|
giB->BaseAbsolue( *(base_propre_eps(2)),tab(2));(base_propre_eps(2))->Normer();
|
|
case 1: giB->BaseAbsolue( *(base_propre_eps(1)),tab(1));(base_propre_eps(1))->Normer();
|
|
break;
|
|
case 2: // en 2D le premier vecteur en en giB et le second en giH !!
|
|
giB->BaseAbsolue( *(base_propre_eps(1)),tab(1));(base_propre_eps(1))->Normer();
|
|
giH->BaseAbsolue( *(base_propre_eps(2)),mat.CoordonneeB_Base_associee(2));
|
|
(base_propre_eps(2))->Normer();
|
|
break;
|
|
|
|
default:break;
|
|
};
|
|
};
|
|
};
|
|
}
|
|
else if (besoin_dir_princ_eps) // cas où on ne veut que les directions principales
|
|
{ Mat_pleine mat(dim,dim); // contiendra par colonne les vecteurs principaux, exprimé en giH
|
|
Coordonnee inter(epsHB->ValPropre(caas,mat)); // dans la matrice mat
|
|
// puis des directions principales, que l'on doit exprimer dans le repère absolue
|
|
Tableau <CoordonneeH > tab = mat.CoordonneeH_Base_associee(); // récup en tab de coor
|
|
// on regarde le cas particulier ou les valeurs propres sont toutes nulles
|
|
// si c'est le cas, on ne fait rien, en sortie on aura des vecteurs propres nulles
|
|
if (inter.Max_val_abs() > ConstMath::petit)
|
|
// et s'il y a eu un pb dans le calcul des valeurs propres ou vecteurs propres on évite
|
|
{if (caas != -1)
|
|
{switch (dim)
|
|
{case 3: giB->BaseAbsolue( *(base_propre_eps(3)),tab(3));(base_propre_eps(3))->Normer();
|
|
giB->BaseAbsolue( *(base_propre_eps(2)),tab(2));(base_propre_eps(2))->Normer();
|
|
case 1: giB->BaseAbsolue( *(base_propre_eps(1)),tab(1));(base_propre_eps(1))->Normer();
|
|
break;
|
|
case 2: // en 2D le premier vecteur en en giB et le second en giH !!
|
|
giB->BaseAbsolue( *(base_propre_eps(1)),tab(1));(base_propre_eps(1))->Normer();
|
|
giH->BaseAbsolue( *(base_propre_eps(2)),mat.CoordonneeB_Base_associee(2));
|
|
(base_propre_eps(2))->Normer();
|
|
break;
|
|
default:break;
|
|
};
|
|
};
|
|
};
|
|
}
|
|
else if (besoin_des_valpropre_deformation)// on ne veut que les valeurs propres
|
|
{ Coordonnee inter(epsHB->ValPropre(caas));
|
|
inter.Change_dim(dim_sortie_tenseur); // on étant la taille éventuellement
|
|
*valPropreEps = inter; // sauvegarde des valeurs propres
|
|
};
|
|
// gestion d'une erreur éventuelle
|
|
if (caas == -1)
|
|
{ cout << "\n warning *** erreur dans le calcul des valeurs propres et-ou vecteurs propres de la deformation";
|
|
if (ParaGlob::NiveauImpression() >= 7) {epsHB->Ecriture(cout);cout << "\n cas = "<< caas ;
|
|
cout << "\Loi_comp_abstraite::Valeurs_Tensorielles_interpoler_ou_calculer(...";};
|
|
cout << endl;
|
|
};
|
|
}; // -- fin de l'encapsulation du cas des déformations
|
|
|
|
{int caas=0; // il faut l'initialiser sinon il peut prendre la valeur du cas précédant
|
|
if (besoin_des_valpropre_vitdef && besoin_dir_princ_D)// on veut les directions et les valeurs propres
|
|
{ Mat_pleine mat(dim,dim); // contiendra par colonne les vecteurs principaux, exprimé en giH
|
|
// 1) calcul des valeurs propres dans un vecteur de travail inter, et des vecteurs propres stockés
|
|
Coordonnee inter(DepsHB->ValPropre(caas,mat)); // dans la matrice mat
|
|
inter.Change_dim(dim_sortie_tenseur); // on étend la taille, dans le cas ou le nb de valeurs
|
|
// propre est inférieur à la dimension de l'espace
|
|
*valPropreDeps = inter; // sauvegarde des valeurs propres
|
|
|
|
// 2) puis des directions principales, que l'on doit exprimer dans le repère absolue
|
|
Tableau <CoordonneeH > tab = mat.CoordonneeH_Base_associee(); // récup en tab de coor
|
|
// on regarde le cas particulier ou les valeurs propres sont toutes nulles
|
|
// si c'est le cas, on ne fait rien, en sortie on aura des vecteurs propres nulles
|
|
if (inter.Max_val_abs() > ConstMath::petit)
|
|
// et s'il y a eu un pb dans le calcul des valeurs propres ou vecteurs propres on évite
|
|
{if (caas != -1)
|
|
{switch (dim)
|
|
{case 3: giB->BaseAbsolue( *(base_propre_D(3)),tab(3));(base_propre_D(3))->Normer();
|
|
giB->BaseAbsolue( *(base_propre_D(2)),tab(2));(base_propre_D(2))->Normer();
|
|
case 1: giB->BaseAbsolue( *(base_propre_D(1)),tab(1));(base_propre_D(1))->Normer();
|
|
break;
|
|
case 2: // en 2D le premier vecteur en en giB et le second en giH !!
|
|
giB->BaseAbsolue( *(base_propre_D(1)),tab(1));(base_propre_D(1))->Normer();
|
|
giH->BaseAbsolue( *(base_propre_D(2)),mat.CoordonneeB_Base_associee(2));
|
|
(base_propre_D(2))->Normer();
|
|
break;
|
|
default:break;
|
|
};
|
|
};
|
|
};
|
|
}
|
|
else if (besoin_dir_princ_D) // cas où on ne veut que les directions principales
|
|
{ Mat_pleine mat(dim,dim); // contiendra par colonne les vecteurs principaux, exprimé en giH
|
|
Coordonnee inter(DepsHB->ValPropre(caas,mat)); // dans la matrice mat
|
|
// puis des directions principales, que l'on doit exprimer dans le repère absolue
|
|
Tableau <CoordonneeH > tab = mat.CoordonneeH_Base_associee(); // récup en tab de coor
|
|
// on regarde le cas particulier ou les valeurs propres sont toutes nulles
|
|
// si c'est le cas, on ne fait rien, en sortie on aura des vecteurs propres nulles
|
|
if (inter.Max_val_abs() > ConstMath::petit)
|
|
// et s'il y a eu un pb dans le calcul des valeurs propres ou vecteurs propres on évite
|
|
{if (caas != -1)
|
|
{switch (dim)
|
|
{case 3: giB->BaseAbsolue( *(base_propre_D(3)),tab(3));(base_propre_D(3))->Normer();
|
|
giB->BaseAbsolue( *(base_propre_D(2)),tab(2));(base_propre_D(2))->Normer();
|
|
case 1: giB->BaseAbsolue( *(base_propre_D(1)),tab(1));(base_propre_D(1))->Normer();
|
|
break;
|
|
case 2: // en 2D le premier vecteur en en giB et le second en giH !!
|
|
giB->BaseAbsolue( *(base_propre_D(1)),tab(1));(base_propre_D(1))->Normer();
|
|
giH->BaseAbsolue( *(base_propre_D(2)),mat.CoordonneeB_Base_associee(2));
|
|
(base_propre_D(2))->Normer();
|
|
break;
|
|
default:break;
|
|
};
|
|
};
|
|
};
|
|
}
|
|
else if (besoin_des_valpropre_vitdef)// on ne veut que les valeurs propres
|
|
{ Coordonnee inter(DepsHB->ValPropre(caas));
|
|
inter.Change_dim(dim_sortie_tenseur); // on étant la taille
|
|
*valPropreDeps = inter; // sauvegarde des valeurs propres
|
|
};
|
|
// gestion d'une erreur éventuelle
|
|
if (caas == -1)
|
|
{ cout << "\n warning *** erreur dans le calcul des valeurs propres et-ou vecteurs propres de la vitesse de deformation";
|
|
if (ParaGlob::NiveauImpression() >= 7) {DepsHB->Ecriture(cout);cout << "\n cas = "<< caas ;
|
|
cout << "\Loi_comp_abstraite::Valeurs_Tensorielles_interpoler_ou_calculer(...";};
|
|
cout << endl;
|
|
};
|
|
}; // -- fin de l'encapsulation du cas des vitesses de déformations
|
|
|
|
|
|
if (besoin_coordonnees)
|
|
(*Mtdt) = def_en_cours->Position_tdt();
|
|
if (besoin_coordonnees_t)
|
|
(*Mt) = def_en_cours->Position_t();
|
|
if (besoin_coordonnees_t0)
|
|
(*M0) = def_en_cours->Position_0();
|
|
|
|
// def éventuelle du vecteur normal: ceci n'est correct qu'avec une métrique 2D
|
|
if (N_surf != NULL)
|
|
{ if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur N_surf necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
// on vérifie que la métrique est correcte
|
|
if (giB->NbVecteur() != 2)
|
|
{if (ParaGlob::NiveauImpression() > 0)
|
|
{cout << "\n *** attention il ne s'agit pas d'un element 2D,"
|
|
<< " le vecteur normal ne sera pas disponible";
|
|
if (ParaGlob::NiveauImpression() > 2)
|
|
cout << "\n Loi_comp_abstraite::Valeurs_Tensorielles_interpoler_ou_calculer(... ";
|
|
};
|
|
cout << endl;
|
|
}
|
|
else // sinon c'est ok
|
|
{// la normale vaut le produit vectoriel des 2 premiers vecteurs
|
|
(*N_surf) = Util::ProdVec_coorBN( (*giB)(1), (*giB)(2));
|
|
N_surf->Normer(); // que l'on norme
|
|
};
|
|
// on n'arrête pas l'exécution, car on pourrait vouloir sortir les normales pour un ensemble
|
|
// d'éléments contenant des volumes, des surfaces, des lignes: bon... il y aura quand même des
|
|
// pb au niveau des iso par exemple, du au fait que l'on va faire des moyennes sur des éléments
|
|
// de type différents (à moins de grouper par type du coup on n'aura pas le warning
|
|
};
|
|
// idem à l'instant t
|
|
if (N_surf_t != NULL)
|
|
{ if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur N_surf_t necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
// on vérifie que la métrique est correcte
|
|
if (giB_t->NbVecteur() != 2)
|
|
{if (ParaGlob::NiveauImpression() > 0)
|
|
{cout << "\n *** attention il ne s'agit pas d'une metrique 2D 2D,"
|
|
<< " le vecteur normal ne sera pas correctement calcule";
|
|
if (ParaGlob::NiveauImpression() > 2)
|
|
cout << "\n Loi_comp_abstraite::Valeurs_Tensorielles_interpoler_ou_calculer(... ";
|
|
};
|
|
cout << endl;
|
|
}
|
|
else // sinon c'est ok
|
|
{// la normale vaut le produit vectoriel des 2 premiers vecteurs
|
|
(*N_surf_t) = Util::ProdVec_coorBN( (*giB_t)(1), (*giB_t)(2));
|
|
N_surf_t->Normer(); // que l'on norme
|
|
};
|
|
};
|
|
// idem à l'instant t0
|
|
if (N_surf_t0 != NULL)
|
|
{ if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur N_surf_0 necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
// on vérifie que la métrique est correcte
|
|
if (giB_0->NbVecteur() != 2)
|
|
{if (ParaGlob::NiveauImpression() > 0)
|
|
{cout << "\n *** attention il ne s'agit pas d'une metrique 2D 2D,"
|
|
<< " le vecteur normal ne sera pas correctement calcule";
|
|
if (ParaGlob::NiveauImpression() > 2)
|
|
cout << "\n Loi_comp_abstraite::Valeurs_Tensorielles_interpoler_ou_calculer(... ";
|
|
};
|
|
cout << endl;
|
|
}
|
|
else // sinon c'est ok
|
|
{// la normale vaut le produit vectoriel des 2 premiers vecteurs
|
|
(*N_surf_t0) = Util::ProdVec_coorBN( (*giB_0)(1), (*giB_0)(2));
|
|
N_surf_t0->Normer(); // que l'on norme
|
|
};
|
|
};
|
|
|
|
// cas du déplacement et de la vitesse
|
|
if (Deplacement != NULL)
|
|
(*Deplacement) = (*Mtdt) - def_en_cours->Position_0();
|
|
if (Vitesse != NULL)
|
|
(*Vitesse) = def_en_cours->VitesseM_tdt();
|
|
|
|
// cas de la deformation équivalente cumulée
|
|
if (def_def_equivalente) {*def_equivalente = ptintmeca_en_cours->Deformation_equi_const()(1);};
|
|
// cas de la deformation duale au sens de mises,
|
|
if (def_duale_mises) {*defDualMises = ptintmeca_en_cours->Deformation_equi_const()(2);};
|
|
// cas de la deformation maxi duale au sens de mises,
|
|
if (def_duale_mises_maxi) {*defDualMisesMaxi = ptintmeca_en_cours->Deformation_equi_const()(3);};
|
|
|
|
// cas des contraintes: mises et tresca
|
|
if (def_sig_mises) {*sig_mises = ptintmeca_en_cours->Sig_equi_const()(1);};
|
|
if (def_sig_tresca) {*sig_tresca = ptintmeca_en_cours->Sig_equi_const()(2);};
|
|
|
|
// //contrainte_tresca
|
|
// if (contraintesTresca)
|
|
// { switch (dim) {case 1: *Tresca=0.5 * (*valPropreSig)(1);break;
|
|
// case 2: *Tresca=0.5 * ((*valPropreSig)(1)-(*valPropreSig)(2));break;
|
|
// case 3: *Tresca=0.5 * ((*valPropreSig)(1)-(*valPropreSig)(3));break;
|
|
// };
|
|
// };
|
|
|
|
// --- cas des grandeurs de la décomposition polaire
|
|
// cas de la déformation
|
|
if (def_SPHERIQUE_EPS) {*spherique_eps = epsHB->Trace()/3.;}; //ParaGlob::Dimension();}; modif 5/2/2012
|
|
double mini_Q = 5.e-5;
|
|
if (def_Q_EPS) {*Q_eps = sqrt(eps_barreHB->II());};
|
|
if (cos3phi_eps)
|
|
{ double Qepsilon = ( def_Q_EPS ? *Q_eps : sqrt(eps_barreHB->II()));
|
|
double Qepsilon3 = Qepsilon * Qepsilon * Qepsilon;
|
|
if (Qepsilon > mini_Q )
|
|
{ // on peut calculer un cos3phi pas débile
|
|
double bIIIb = eps_barreHB->III() / 3.;
|
|
*cos3phi_eps = 3. * sqrt(6.) * bIIIb/ Qepsilon3;
|
|
}
|
|
else *cos3phi_eps=0.; // sinon on le met à 0
|
|
};
|
|
// cas de la contrainte
|
|
if (def_SPHERIQUE_SIG) {*spherique_sig = sigHB->Trace()/3.;}; //ParaGlob::Dimension();}; modif 5/2/2012
|
|
if (def_Q_SIG) {*Q_sig = sqrt(sig_barreHB->II());};
|
|
if (cos3phi_sig)
|
|
{ double Qsig = ( def_Q_SIG ? *Q_sig : sqrt(sig_barreHB->II()));
|
|
double Qsig3 = Qsig * Qsig * Qsig;
|
|
if (Qsig > mini_Q )
|
|
{ // on peut calculer un cos3phi pas débile
|
|
double bIIIb = sig_barreHB->III() / 3.;
|
|
*cos3phi_sig = 3. * sqrt(6.) * bIIIb/ Qsig3;
|
|
}
|
|
else *cos3phi_sig=0.; // sinon on le met à 0
|
|
};
|
|
// cas de la vitesse de déformation
|
|
if (def_SPHERIQUE_DEPS) {*spherique_Deps = DepsHB->Trace()/3.;}; //ParaGlob::Dimension();}; modif 5/2/2012
|
|
if (def_Q_DEPS) {*Q_Deps = sqrt(Deps_barreHB->II());};
|
|
if (cos3phi_Deps)
|
|
{ double QDepsilon = ( def_Q_DEPS ? *Q_Deps : sqrt(Deps_barreHB->II()));
|
|
double QDepsilon3 = QDepsilon * QDepsilon * QDepsilon;
|
|
if (QDepsilon > mini_Q )
|
|
{ // on peut calculer un cos3phi pas débile
|
|
double bIIIb = Deps_barreHB->III() / 3.;
|
|
*cos3phi_Deps = 3. * sqrt(6.) * bIIIb/ QDepsilon3;
|
|
}
|
|
else *cos3phi_Deps=0.; // sinon on le met à 0
|
|
};
|
|
|
|
// delete des tenseurs
|
|
if (sigHB != NULL) delete sigHB;
|
|
if (epsHB != NULL) delete epsHB;
|
|
if (DepsHB != NULL) delete DepsHB;
|
|
if (eps_barreHB != NULL) delete eps_barreHB;
|
|
if (Deps_barreHB != NULL) delete Deps_barreHB;
|
|
if (sig_barreHB != NULL) delete sig_barreHB;
|
|
// effacement conditionnel
|
|
if (besoin_des_contraintes && !contrainteCourante) delete sigHH;
|
|
if (besoin_des_deformation && !deformationCourante) delete epsBB;
|
|
if (vitesseDeformationCourante && !vitesseDeformationCourante) delete DepsBB;
|
|
if (besoin_des_valpropre_deformation && !defPrincipales) delete valPropreEps;
|
|
if (besoin_des_valpropre_vitdef && !vitPrincipales) delete valPropreDeps ;
|
|
if (besoin_des_valpropre_sigma && !sigmaPrincipales) delete valPropreSig;
|
|
// pointeurs de matrice
|
|
if (Aa0 != NULL) delete Aa0;
|
|
if (Aafin != NULL) delete Aafin;
|
|
if (gamma0 != NULL) delete gamma0;
|
|
if (gammafin != NULL) delete gammafin;
|
|
if (beta0 != NULL) delete beta0;
|
|
if (betafin != NULL) delete betafin;
|
|
|
|
// liberation des tenseurs intermediaires
|
|
LibereTenseur();
|
|
};
|
|
|
|
// affichage de la liste des grandeurs possible à calculer avec Valeur_multi_interpoler_ou_calculer
|
|
void Loi_comp_abstraite::Affichage_grandeurs_Valeurs_Tensorielles_interpoler_ou_calculer()
|
|
{ cout << "\n grandeurs tensorielles ou evoluees disponibles :";
|
|
cout << "\n CONTRAINTE_COURANTE, DEFORMATION_COURANTE, VITESSE_DEFORMATION_COURANTE "
|
|
<< "\n ALMANSI, GREEN_LAGRANGE, LOGARITHMIQUE, DELTA_DEF, ALMANSI_TOTAL"
|
|
<< "\n GREEN_LAGRANGE_TOTAL, LOGARITHMIQUE_TOTALE, DEF_PRINCIPALES"
|
|
<< "\n SIGMA_PRINCIPALES, VIT_PRINCIPALES, SPHERIQUE_EPS, Q_EPS, COS3PHI_EPS"
|
|
<< "\n SPHERIQUE_SIG, Q_SIG, COS3PHI_SIG, SPHERIQUE_DEPS, Q_DEPS"
|
|
<< "\n COS3PHI_DEPS, DIRECTIONS_PRINC_SIGMA, DIRECTIONS_PRINC_DEF"
|
|
<< "\n DIRECTIONS_PRINC_D, NUM_ELEMENT, NUM_MAIL_ELEM, NUM_PTI"
|
|
<< "\n POSITION_GEOMETRIQUE, POSITION_GEOMETRIQUE_t, POSITION_GEOMETRIQUE_t0, "
|
|
<< "\n si pertinent: REPERE_LOCAL_ORTHO, REPERE_LOCAL_H, REPERE_LOCAL_B"
|
|
<< "\n si pertinent: NN_SURF, NN_SURF_t, NN_SURF_t0, DEPLACEMENT, VITESSE"
|
|
<< "\n DEF_DUALE_MISES, DEF_EQUIVALENTE, DEF_DUALE_MISES_MAXI "
|
|
<< "\n ,CONTRAINTE_MISES,CONTRAINTE_TRESCA"
|
|
;
|
|
};
|
|
|
|
|
|
// récupération de valeurs interpolées pour les grandeur ici considéré quelconque enu
|
|
// ces grandeurs ne sont pas définies dans la liste des Ddl_enum_etendu : ex mises à t
|
|
// ou le numéro de l'élément etc.
|
|
// absolue: indique si oui ou non on sort les tenseurs dans la base absolue ou une base particulière
|
|
// une seule des 3 métriques doit-être renseigné, les autres doivent être un pointeur nul
|
|
// exclure_Q: donne une liste de grandeur quelconque à exclure de la recherche
|
|
// parce que par exemple, ils sont calculés par ailleurs
|
|
// on peut également ne pas définir de métrique, dans ce cas on ne peut pas calculer certaines grandeurs
|
|
// -> il y a vérification
|
|
// retour: la list li_quelc qui en entrée doit avoir la même dimension que tqi
|
|
void Loi_comp_abstraite::Valeurs_quelconque_interpoler_ou_calculer
|
|
(bool absolue, Enum_dure temps
|
|
,const Tableau <EnumTypeQuelconque>& tqi
|
|
,List_io<TypeQuelconque>& li_quelc
|
|
,const Met_abstraite::Impli* ex_impli
|
|
,const Met_abstraite::Expli_t_tdt* ex_expli_tdt
|
|
,const Met_abstraite::Umat_cont* ex_umat
|
|
,const List_io<EnumTypeQuelconque>* exclure_Q
|
|
)
|
|
|
|
{ // on a besoin a priori de ptintmeca_en_cours, donc s'il n'est pas définit -> erreur
|
|
#ifdef MISE_AU_POINT
|
|
if (ptintmeca_en_cours == NULL)
|
|
{cout << "\n *** cas non prevu : aucun conteneur de point d'integration transmis "
|
|
<< "\n Loi_comp_abstraite::Valeurs_quelconque_interpoler_ou_calculer(..." << endl;
|
|
Sortie(1);
|
|
};
|
|
if (def_en_cours == NULL)
|
|
{cout << "\n *** cas non prevu : la deformation n'est pas transmise "
|
|
<< "\n Loi_comp_abstraite::Valeurs_quelconque_interpoler_ou_calculer(..." << endl;
|
|
Sortie(1);
|
|
};
|
|
#endif
|
|
// ----- def de grandeurs de travail
|
|
// def de la dimension des tenseurs
|
|
// il y a deux pb a gérer: 1) le fait que la dimension absolue peut-être différente de la dimension des tenseurs
|
|
// 2) le fait que l'on veut une sortie dans une base ad hoc ou pas
|
|
int dim = ptintmeca_en_cours->EpsBB_const().Dimension();
|
|
int dim_sortie_tenseur = dim;
|
|
// dans le cas ou l'on veut une sortie en base absolue, il faut que dim_sortie_tenseur = la dimension de la base absolue
|
|
int dim_espace = ParaGlob::Dimension();
|
|
if (absolue)
|
|
dim_sortie_tenseur = dim_espace;
|
|
// pour ne faire qu'un seul test ensuite
|
|
bool prevoir_change_dim_tenseur = false;
|
|
// initialement on faisait le test suivant,
|
|
// if ((absolue) && (dim != dim_sortie_tenseur))
|
|
if (absolue)
|
|
// mais en fait, quand on sort en absolu on est obligé d'utiliser un tenseur intermédiaire
|
|
// car BaseAbsolue(.. modifie tenseur passé en paramètre, donc dans tous les cas de sortie absolue
|
|
// il faut un tenseur intermédiaire qui a ou non une dimension différente
|
|
prevoir_change_dim_tenseur = true;
|
|
|
|
// éléments de métrique et matrices de passage
|
|
TenseurHH* gijHH;TenseurBB* gijBB;BaseB* giB; BaseH* giH_0;BaseH* giH;
|
|
Mat_pleine jB0(dim,dim),jBfin(dim,dim);
|
|
BaseB* giB_0;BaseB* giB_t;
|
|
bool pas_de_metrique_dispo = false; // init
|
|
|
|
if (ex_impli != NULL)
|
|
{ gijHH = ex_impli->gijHH_tdt;gijBB = ex_impli->gijBB_tdt;
|
|
giB = ex_impli->giB_tdt; giH_0 = ex_impli->giH_0;giH = ex_impli->giH_tdt;
|
|
giB_t = ex_impli->giB_t; giB_0 = ex_impli->giB_0;
|
|
}
|
|
else if (ex_expli_tdt != NULL)
|
|
{gijHH = ex_expli_tdt->gijHH_tdt;gijBB = ex_expli_tdt->gijBB_tdt;
|
|
giB = ex_expli_tdt->giB_tdt; giH_0 = ex_expli_tdt->giH_0;giH = ex_expli_tdt->giH_tdt;
|
|
giB_t = ex_expli_tdt->giB_t; giB_0 = ex_expli_tdt->giB_0;
|
|
}
|
|
else if (ex_umat != NULL)
|
|
{gijHH = ex_umat->gijHH_t;gijBB = ex_umat->gijBB_t;
|
|
giB = giB_t = ex_umat->giB_t; giH_0 = ex_umat->giH_0;giH = ex_umat->giH_t;
|
|
giB_0 = ex_umat->giB_0;
|
|
}
|
|
else
|
|
{ pas_de_metrique_dispo = true;
|
|
// cout << "\n *** cas non prevu : aucune metrique transmise "
|
|
// << "\n Loi_comp_abstraite::Valeurs_quelconque_interpoler_ou_calculer(..." << endl;
|
|
// Sortie(1);
|
|
};
|
|
|
|
// def de tenseurs pour la sortie
|
|
// les tenseurs restants en locale
|
|
|
|
// pour les valeurs propres
|
|
|
|
// pour les vecteurs propres
|
|
|
|
// pour les bases
|
|
Tableau <Coordonnee *> base_ad_hoc , base_giH , base_giB;
|
|
|
|
|
|
// --- dev d'un ensemble de variable booléenne pour gérer les sorties en une passe -----
|
|
// on se réfère au informations définit dans la méthode: Les_type_evolues_internes()
|
|
bool besoin_rep_local_ortho=false;
|
|
bool besoin_rep_giH = false; bool besoin_rep_giB = false;
|
|
|
|
|
|
// init pour l'utilisation de la liste d'exclusion
|
|
List_io<EnumTypeQuelconque>::const_iterator itt_deb;
|
|
List_io<EnumTypeQuelconque>::const_iterator itt_fin;
|
|
if (exclure_Q != NULL)
|
|
{ itt_deb = exclure_Q->begin();
|
|
itt_fin = exclure_Q->end();
|
|
};
|
|
// on va boucler sur les énumérés quelconque
|
|
int nb_tqi = tqi.Taille();
|
|
List_io <TypeQuelconque >::iterator ipq=li_quelc.begin();
|
|
for (int i_tqi = 1;i_tqi <= nb_tqi;i_tqi++,ipq++ )
|
|
// on initialise ces variables booléennes et les conteneurs
|
|
{EnumTypeQuelconque& enuconq = tqi(i_tqi);
|
|
switch (enuconq)
|
|
{
|
|
case CONTRAINTE_MISES :
|
|
{Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
(*gr.ConteneurDouble()) = ptintmeca_en_cours->Sig_equi_const()(1);
|
|
break;
|
|
}
|
|
case CONTRAINTE_TRESCA :
|
|
{Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
(*gr.ConteneurDouble()) = ptintmeca_en_cours->Sig_equi_const()(2);
|
|
break;
|
|
}
|
|
case CONTRAINTE_MISES_T :
|
|
{Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
(*gr.ConteneurDouble()) = ptintmeca_en_cours->Sig_equi_t_const()(1);
|
|
break;
|
|
}
|
|
case CONTRAINTE_TRESCA_T :
|
|
{Grandeur_scalaire_double& gr= *((Grandeur_scalaire_double*) ((*ipq).Grandeur_pointee()));
|
|
(*gr.ConteneurDouble()) = ptintmeca_en_cours->Sig_equi_t_const()(2);
|
|
break;
|
|
}
|
|
case NUM_ELEMENT:
|
|
{Grandeur_scalaire_entier& gr= *((Grandeur_scalaire_entier*) ((*ipq).Grandeur_pointee()));
|
|
(*gr.ConteneurEntier())=ptintmeca_en_cours->Nb_ele();
|
|
break;
|
|
}
|
|
case NUM_MAIL_ELEM:
|
|
{Grandeur_scalaire_entier& gr= *((Grandeur_scalaire_entier*) ((*ipq).Grandeur_pointee()));
|
|
(*gr.ConteneurEntier())=ptintmeca_en_cours->Nb_mail();
|
|
break;
|
|
}
|
|
case NUM_PTI:
|
|
{Grandeur_scalaire_entier& gr= *((Grandeur_scalaire_entier*) ((*ipq).Grandeur_pointee()));
|
|
(*gr.ConteneurEntier())=ptintmeca_en_cours->Nb_pti();
|
|
break;
|
|
}
|
|
case REPERE_LOCAL_ORTHO :
|
|
{base_ad_hoc.Change_taille(dim_espace);
|
|
Tab_Grandeur_Coordonnee& gr= *((Tab_Grandeur_Coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur REPERE_LOCAL_ORTHO necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
|
|
// calcul de la base
|
|
switch (dim_espace) {case 3: gr(3).Zero(); case 2: gr(2).Zero(); default:break;};//init
|
|
switch (dim_espace) {case 3: base_ad_hoc(3) = &(gr(3));
|
|
case 2: base_ad_hoc(2) = &(gr(2));
|
|
case 1: base_ad_hoc(1) = &(gr(1));
|
|
default:break;
|
|
};
|
|
if ((!absolue)&&(dim_espace==3)&&(dim==2))
|
|
// cas d'éléments 2D, pour lesquels on veut un repère local ad hoc
|
|
// on ramène une base à 3 vecteurs
|
|
{ *(base_ad_hoc(1)) = jBfin(1,1) * giB->Coordo(1) + jBfin(2,1) * giB->Coordo(2);
|
|
*(base_ad_hoc(2)) = jBfin(1,2) * giB->Coordo(1) + jBfin(2,2) * giB->Coordo(2);
|
|
*(base_ad_hoc(3)) = Util::ProdVec_coor(*(base_ad_hoc(1)),*(base_ad_hoc(2)));
|
|
}
|
|
else if((!absolue)&&(dim_espace>1)&&(dim==1))
|
|
// cas d'éléments 1D, dans un espace 2D ou 3D
|
|
// on ramène un seul vecteur non nul, les autres ne peuvent être calculé sans info supplémentaire
|
|
{ *(base_ad_hoc(1)) = jBfin(1,1) * giB->Coordo(1);
|
|
(base_ad_hoc(2))->Zero(); (base_ad_hoc(3))->Zero(); // init à 0 par défaut
|
|
}
|
|
else // dans tous les autres cas
|
|
{ switch (dim_espace) // on se contente de ramener le repère identité
|
|
{case 3: (base_ad_hoc(3))->Zero();(*(base_ad_hoc(3)))(3)=1.;
|
|
case 2: (base_ad_hoc(2))->Zero();(*(base_ad_hoc(2)))(2)=1.;
|
|
case 1: (base_ad_hoc(1))->Zero();(*(base_ad_hoc(1)))(1)=1.;
|
|
default:break;
|
|
};
|
|
};
|
|
break;
|
|
}
|
|
case REPERE_LOCAL_H :
|
|
{base_giH.Change_taille(dim);
|
|
Tab_Grandeur_Coordonnee& gr= *((Tab_Grandeur_Coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur REPERE_LOCAL_H necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
|
|
switch (dim_espace) {case 3: gr(3).Zero(); case 2: gr(2).Zero(); default:break;};//init
|
|
switch (dim) {case 3: base_giH(3) = &(gr(3));
|
|
case 2: base_giH(2) = &(gr(2));
|
|
case 1: base_giH(1) = &(gr(1));
|
|
default:break;
|
|
};
|
|
|
|
// calcul de la base
|
|
switch (dim) {case 3: *(base_giH(3)) = giH->Coordo(3);
|
|
case 2: *(base_giH(2)) = giH->Coordo(2);
|
|
case 1: *(base_giH(1)) = giH->Coordo(1);
|
|
default:break;
|
|
};
|
|
// stockage
|
|
TypeQuelconque typQ6(REPERE_LOCAL_H,SIG11,gr);
|
|
li_quelc.push_back(typQ6);
|
|
break;
|
|
}
|
|
case REPERE_LOCAL_B :
|
|
{base_giB.Change_taille(dim);
|
|
Tab_Grandeur_Coordonnee& gr= *((Tab_Grandeur_Coordonnee*) ((*ipq).Grandeur_pointee()));
|
|
if (pas_de_metrique_dispo)
|
|
{ cout << "\n ***erreur, la grandeur REPERE_LOCAL_B necessite la donnee de la metrique "
|
|
<< " or elle n'est pas ici disponible !! ";
|
|
Sortie(1);
|
|
};
|
|
|
|
switch (dim_espace) {case 3: gr(3).Zero(); case 2: gr(2).Zero(); default:break;};//init
|
|
switch (dim) {case 3: base_giB(3) = &(gr(3));
|
|
case 2: base_giB(2) = &(gr(2));
|
|
case 1: base_giB(1) = &(gr(1));
|
|
default:break;
|
|
};
|
|
|
|
// calcul de la base
|
|
switch (dim) {case 3: *(base_giB(3)) = giB->Coordo(3);
|
|
case 2: *(base_giB(2)) = giB->Coordo(2);
|
|
case 1: *(base_giB(1)) = giB->Coordo(1);
|
|
default:break;
|
|
};
|
|
// stockage
|
|
TypeQuelconque typQ6(REPERE_LOCAL_B,SIG11,gr);
|
|
li_quelc.push_back(typQ6);
|
|
break;
|
|
}
|
|
default :
|
|
{ // on regarde si la grandeur en fait n'est pas à calculer
|
|
bool a_atraiter = true;
|
|
if (exclure_Q != NULL)
|
|
if (find(itt_deb,itt_fin,enuconq) != itt_fin)
|
|
a_atraiter = false;
|
|
if (a_atraiter)
|
|
// cas où ce n'est pas à exclure, donc cela manque
|
|
{if (ParaGlob::NiveauImpression() > 0)
|
|
{cout << "\n warning : attention cas non traite: "
|
|
<< NomTypeQuelconque(enuconq) << "!\n";
|
|
if (ParaGlob::NiveauImpression() > 5)
|
|
cout << "\n Loi_comp_abstraite::Valeurs_quelconque_interpoler_ou_calculer(....";
|
|
Sortie(1);
|
|
};
|
|
};
|
|
}
|
|
};
|
|
};
|
|
|
|
|
|
|
|
// delete des tenseurs
|
|
|
|
// liberation des tenseurs intermediaires
|
|
LibereTenseur();
|
|
};
|
|
|
|
// affichage de la liste des grandeurs possible à calculer avec Valeur_multi_interpoler_ou_calculer
|
|
void Loi_comp_abstraite::Affichage_grandeurs_Valeurs_quelconque_interpoler_ou_calculer()
|
|
{ cout << "\n grandeurs quelconques disponibles :";
|
|
cout << "\n si pertinent: REPERE_LOCAL_ORTHO, REPERE_LOCAL_H, REPERE_LOCAL_B"
|
|
<< "\n ,CONTRAINTE_MISES_T,CONTRAINTE_TRESCA_T"
|
|
;
|
|
};
|
|
|
|
|
|
|
|
// calcul de la valeur et retour dans tab_ret d'une fonction nD
|
|
// à l'aide des grandeurs disponibles pour la loi de comportement
|
|
// nb_retour: nombre de composantes attendues en retour, si > 0
|
|
// deja_calculer: donne une liste de grandeur Ddl_enum_etendu et quelconque
|
|
// à exclure de la recherche car ils doivent avoir été calculés par ailleurs
|
|
// c'est une donnée d'entrée qui peut-être utilisée pour l'appel de la fonction nD
|
|
// list_save : est censé contenir la ou les save_result à consulter pour avoir
|
|
// des infos supplémentaires
|
|
Tableau <double> & Loi_comp_abstraite::Loi_comp_Valeur_FnD_Evoluee
|
|
(Fonction_nD* fct,int nb_retour
|
|
,const Met_abstraite::Impli* ex_impli
|
|
,const Met_abstraite::Expli_t_tdt* ex_expli_tdt
|
|
,const Met_abstraite::Umat_cont* ex_umat
|
|
,const List_io<Ddl_etendu>* deja_calculer_etend
|
|
,const List_io<const TypeQuelconque *>* deja_calculer_Q
|
|
,list <SaveResul*>* list_save
|
|
)
|
|
{ // ici on utilise les variables connues aux pti, ou calculées à partir de
|
|
// on commence par récupérer les conteneurs des grandeurs à fournir
|
|
// 1) la partie grandeurs évoluées
|
|
List_io <Ddl_enum_etendu>& li_enu_scal = fct->Li_enu_etendu_scalaire();
|
|
List_io <TypeQuelconque >& li_quelc = fct->Li_equi_Quel_evolue();
|
|
// on récupère le type d'expression des tenseurs
|
|
bool absolue = fct->Absolue();
|
|
|
|
// --- on s'occupe des Ddl_enum_etendu nécessaires pour l'appel de la fonction nD
|
|
List_io<Ddl_enum_etendu> exclure_dd_etend;
|
|
// --> on rempli la liste à exclure
|
|
if (deja_calculer_etend != NULL)
|
|
{ List_io<Ddl_etendu>::const_iterator ik,ikfin=deja_calculer_etend->end();
|
|
for (ik= deja_calculer_etend->begin(); ik != ikfin;ik++)
|
|
exclure_dd_etend.push_back((*ik).Const_DdlEnumEtendu());
|
|
};
|
|
// on va utiliser la méhode Valeur_multi_interpoler_ou_calculer
|
|
// pour les grandeurs strictement scalaire
|
|
Tableau <double> val_ddl_enum(Valeur_multi_interpoler_ou_calculer
|
|
(absolue,TEMPS_tdt,li_enu_scal,ex_impli,ex_expli_tdt,ex_umat,&exclure_dd_etend));
|
|
|
|
// on va récupérer les infos qui ont été exclus
|
|
int index = 1;
|
|
if (deja_calculer_etend != NULL)
|
|
{ List_io<Ddl_etendu>::const_iterator ik,ikfin=deja_calculer_etend->end();
|
|
List_io <Ddl_enum_etendu>::iterator il,ilfin=li_enu_scal.end();
|
|
for (il = li_enu_scal.begin(); il != ilfin; il++,index++)
|
|
{// on parcours la liste: normalement il n'y a pas beaucoup d'éléments ...
|
|
// donc ce n'est "peut-être" pas trop couteux
|
|
for (ik= deja_calculer_etend->begin(); ik != ikfin;ik++)
|
|
{if ((*ik).Const_DdlEnumEtendu() == (*il))
|
|
// on a trouvé
|
|
{val_ddl_enum(index) = (*ik).ConstValeur();
|
|
break;
|
|
};
|
|
};
|
|
};
|
|
};
|
|
|
|
// pour les grandeurs quelconque, on va exclure certaines grandeurs de l'appel de
|
|
// Valeur_multi_interpoler_ou_calculer(..)
|
|
// pour cela on se sert d'une liste locale que l'on abonde ensuite avec la liste passée
|
|
// en paramètre si elle existe
|
|
|
|
List_io<EnumTypeQuelconque> exclure_local;
|
|
if (list_save != NULL)
|
|
{// on essaie de récupérer les types quelconques
|
|
// récupération des type quelconque sous forme d'un arbre pour faciliter la recherche
|
|
list <SaveResul*>::iterator isave=list_save->begin(); // pour les saveResul des lois
|
|
list <SaveResul*>::iterator isavedebut=list_save->begin(); // pour les saveResul des lois
|
|
list <SaveResul*>::iterator isavefin=list_save->end(); // pour les saveResul des lois
|
|
List_io <TypeQuelconque>::iterator it,itfin = li_quelc.end();
|
|
|
|
for (it = li_quelc.begin(); it != itfin; it++)
|
|
{bool valeur_recuperer = false; // pour savoir s'il y a eu récupération
|
|
EnumTypeQuelconque enu=(*it).EnuTypeQuelconque().EnumTQ();
|
|
// on boucle sur les save_results pour récupérer les types quelconques
|
|
for (isave = isavedebut; isave != isavefin;isave++)
|
|
// l'idée ici est de regarder si on ne trouve pas une des grandeurs demandées dans la map
|
|
{const map < EnumTypeQuelconque , TypeQuelconque, std::less < EnumTypeQuelconque> >*
|
|
map_quelcon = (*isave)->Map_type_quelconque();
|
|
map < EnumTypeQuelconque , TypeQuelconque, std::less < EnumTypeQuelconque> >::const_iterator imap;
|
|
if (map_quelcon != NULL) // sinon il n'y a pas de map
|
|
{imap = map_quelcon->find(enu);
|
|
if (imap != map_quelcon->end())
|
|
{ // on a trouvé la grandeur
|
|
switch (Type_de_grandeur_associee(enu))
|
|
{ case SCALAIRE_DOUBLE:
|
|
{ const Grandeur_scalaire_double& tyTQ= *((Grandeur_scalaire_double*)
|
|
(*imap).second.Const_Grandeur_pointee());
|
|
// on renseigne l'argument
|
|
(*(*it).Grandeur_pointee()) = tyTQ;
|
|
valeur_recuperer = true;
|
|
break;
|
|
}
|
|
case SCALAIRE_ENTIER:
|
|
{ const Grandeur_scalaire_entier& tyTQ= *((Grandeur_scalaire_entier*)
|
|
(*imap).second.Const_Grandeur_pointee());
|
|
// on renseigne l'argument
|
|
(*(*it).Grandeur_pointee()) = tyTQ;
|
|
valeur_recuperer = true;
|
|
break;
|
|
}
|
|
default:
|
|
{cout << "\n erreur fatale dans l'utilisation de la grandeur locale,"
|
|
<< NomTypeQuelconque(enu)
|
|
<< " necessaire pour le calcul de la ponderation "
|
|
<< " cette grandeur n'est pas un scalaire, pour l'instant "
|
|
<< " on ne sait pas comment l'utiliser !! "
|
|
<< "\n Loi_comp_abstraite::Loi_comp_Valeur_FnD_Evoluee(... ";
|
|
Sortie(1);
|
|
};
|
|
break;
|
|
};
|
|
// on sort de la boucle
|
|
break;
|
|
};
|
|
|
|
// si la grandeur a été récupérée, on l'exclue de la liste à transmettre
|
|
// à la méthode Valeurs_Tensorielles_interpoler_ou_calculer
|
|
if (valeur_recuperer)
|
|
exclure_local.push_back(enu);
|
|
};
|
|
// on merge les des deux exclure
|
|
if (deja_calculer_Q != NULL)
|
|
{List_io <const TypeQuelconque *>::const_iterator iv,ivfin = deja_calculer_Q->end();
|
|
for (iv=deja_calculer_Q->begin();iv != ivfin;iv++)
|
|
{ if (*iv != NULL)
|
|
{EnumTypeQuelconque enutq = (*iv)->EnuTypeQuelconque().EnumTQ();
|
|
exclure_local.push_back(enutq);
|
|
}
|
|
}
|
|
};
|
|
exclure_local.sort();
|
|
exclure_local.unique();
|
|
};
|
|
};
|
|
};
|
|
|
|
// on utilise la méthode Valeurs_Tensorielles_interpoler_ou_calculer
|
|
// pour les Coordonnees et Tenseur
|
|
Valeurs_Tensorielles_interpoler_ou_calculer
|
|
(absolue,TEMPS_tdt,li_quelc,ex_impli,ex_expli_tdt,ex_umat,&exclure_local);
|
|
|
|
// arrivée ici toutes les grandeurs évoluées de la fonction sont connues
|
|
|
|
// 2) on s'occupe maintenant des grandeurs quelconques autres qu'évoluées
|
|
// celles-ci , si elles ne sont pas déjà connues via la liste d'exclusion
|
|
// sont supposées être uniquement dans la map
|
|
// -> si on ne les trouve pas ==> pb !
|
|
const Tableau <EnumTypeQuelconque>& tqi = fct->Tab_enu_quelconque();
|
|
int taille_tqi = tqi.Taille();
|
|
Tableau < const TypeQuelconque * > tquelc(taille_tqi);
|
|
|
|
// on réutilise la map qui est aussi sensé contenir les quelconques autres
|
|
if (taille_tqi != 0)
|
|
{if(list_save == NULL)
|
|
{cout << "\n erreur fatale dans l'utilisation de grandeurs quelconque,"
|
|
<< " necessaire pour le calcul de la fonction nD "
|
|
<< " les grandeurs ne sont pas disponibles, a priori ??? "
|
|
<< "\n Loi_comp_abstraite::Loi_comp_Valeur_FnD_Evoluee(... ";
|
|
Sortie(1);
|
|
}
|
|
else
|
|
{ // on essaie de récupérer les types quelconques
|
|
// --- préparation pour les grandeurs déjà calculées et passée en paramètre
|
|
List_io<const TypeQuelconque *>::const_iterator ik,ikfin,ikdebut;
|
|
if (deja_calculer_Q != NULL)
|
|
{ ikfin = deja_calculer_Q->end();
|
|
ikdebut = deja_calculer_Q->begin();
|
|
};
|
|
|
|
// récupération des type quelconque sous forme d'un arbre pour faciliter la recherche
|
|
list <SaveResul*>::iterator isave=list_save->begin(); // pour les saveResul des lois
|
|
list <SaveResul*>::iterator isavedebut=list_save->begin(); // pour les saveResul des lois
|
|
list <SaveResul*>::iterator isavefin=list_save->end(); // pour les saveResul des lois
|
|
|
|
for (int i = 1; i <= taille_tqi; i++)
|
|
{bool valeur_recuperer = false; // pour savoir s'il y a eu récupération
|
|
EnumTypeQuelconque enu= tqi(i);
|
|
//a) on regarde si la grandeur ne fait pas partie des grandeurs déjà connues
|
|
// via l'exclusion passée en paramètre
|
|
if (deja_calculer_Q != NULL)
|
|
{// on parcours la liste: normalement il n'y a pas beaucoup d'éléments ...
|
|
// donc ce n'est "peut-être" pas trop couteux
|
|
for (ik= ikdebut; ik != ikfin;ik++)
|
|
{if ((*ik)->EnuTypeQuelconque().EnumTQ() == enu)
|
|
// on a trouvé
|
|
{tquelc(i) = (*ik);
|
|
valeur_recuperer = true;
|
|
break;
|
|
};
|
|
};
|
|
};
|
|
|
|
// on continue si on n'a pas récupéré
|
|
// on boucle sur les save_results pour récupérer les types quelconques
|
|
if (!valeur_recuperer)
|
|
for (isave = isavedebut; isave != isavefin;isave++)
|
|
// l'idée ici est de regarder si on ne trouve pas une des grandeurs demandées dans la map
|
|
{const map < EnumTypeQuelconque , TypeQuelconque, std::less < EnumTypeQuelconque> >*
|
|
map_quelcon = (*isave)->Map_type_quelconque();
|
|
map < EnumTypeQuelconque , TypeQuelconque, std::less < EnumTypeQuelconque> >::const_iterator imap;
|
|
if (map_quelcon != NULL) // sinon il n'y a pas de map
|
|
{imap = map_quelcon->find(enu);
|
|
if (imap != map_quelcon->end())
|
|
{ // on a trouvé la grandeur
|
|
tquelc(i) = &(*imap).second;
|
|
valeur_recuperer = true;
|
|
break;
|
|
};
|
|
};
|
|
};
|
|
|
|
if (!valeur_recuperer)// si on n'a pas trouvé, pb car on ne pourra pas fournir l'info nécessaire
|
|
// pour la fonction nD
|
|
{cout << "\n erreur fatale dans l'utilisation de la grandeur locale,"
|
|
<< NomTypeQuelconque(enu)
|
|
<< " necessaire pour le calcul de la fonction nD "
|
|
<< " cette grandeur n'est pas disponible, a priori ??? "
|
|
<< "\n Loi_comp_abstraite::Loi_comp_Valeur_FnD_Evoluee(... ";
|
|
Sortie(1);
|
|
};
|
|
};
|
|
};
|
|
};
|
|
|
|
try
|
|
{// maintenant calcul de la valeur et retour dans tab_ret
|
|
// sauf les valeurs à exclure
|
|
Tableau <double> & tab_val = fct->Valeur_FnD_Evoluee(&val_ddl_enum,&li_enu_scal,&li_quelc,&tquelc,NULL);
|
|
#ifdef MISE_AU_POINT
|
|
if (nb_retour > 0)
|
|
{if (tab_val.Taille() != nb_retour)
|
|
{ cout << "\nErreur : la fonction nD relative " << fct->NomFonction()
|
|
<< " doit calculer "<< nb_retour << " or le tableau de retour est de taille "
|
|
<< tab_val.Taille() << " ce n'est pas normal !\n";
|
|
cout << "\n **** erreur: Loi_comp_abstraite::Loi_comp_Valeur_FnD_Evoluee \n";
|
|
Sortie(1);
|
|
};
|
|
};
|
|
#endif
|
|
// on retourne les infos
|
|
return tab_val;
|
|
}
|
|
catch(ErrCalculFct_nD &e)
|
|
{ cout << "\n Loi_comp_abstraite::Loi_comp_Valeur_FnD_Evoluee \n";
|
|
cout << "\n ** erreur dans l'appel de la fonction " << fct->NomFonction();
|
|
//cout << "\n pour debug Loi_comp_abstraite::Loi_comp_Valeur_FnD_Evoluee \n";
|
|
//Tableau <double> & tab_val = fct->Valeur_FnD_Evoluee(&val_ddl_enum,&li_enu_scal,&li_quelc,&tquelc,NULL);
|
|
throw e;
|
|
Sortie(1);
|
|
}
|
|
|
|
};
|
|
|
|
|
|
// calcul l'affichage, si celui-ci dépend d'une fonction nD
|
|
// ne doit être appelé que si la fonction nD existe (pas de vérification)
|
|
// en fait est utilisé uniquement par la méthode inline: Permet_affichage()
|
|
int Loi_comp_abstraite::Cal_permet_affichage()
|
|
{
|
|
// il faut calculer la fonction nD
|
|
// ici on utilise les variables connues aux pti, ou calculées à partir de
|
|
// on commence par récupérer les conteneurs des grandeurs à fournir
|
|
List_io <Ddl_enum_etendu>& li_enu_scal = permet_affich_loi_nD->Li_enu_etendu_scalaire();
|
|
List_io <TypeQuelconque >& li_quelc = permet_affich_loi_nD->Li_equi_Quel_evolue();
|
|
bool absolue = true; // on se place systématiquement en absolu
|
|
|
|
// on va utiliser la méhode Valeur_multi_interpoler_ou_calculer
|
|
// pour les grandeurs strictement scalaire
|
|
// ici toutes les métriques sont NULL (les 3 premiers NULL)
|
|
// pas d'exclusion de Ddl_enum_etendu (le dernier NULL)
|
|
Tableau <double> val_ddl_enum(Valeur_multi_interpoler_ou_calculer
|
|
(absolue,TEMPS_tdt,li_enu_scal,NULL,NULL,NULL,NULL));
|
|
|
|
// on utilise la méthode Valeurs_Tensorielles_interpoler_ou_calculer
|
|
// pour les Coordonnees et Tenseur
|
|
Valeurs_Tensorielles_interpoler_ou_calculer
|
|
(absolue,TEMPS_tdt,li_quelc,NULL,NULL,NULL,NULL);
|
|
|
|
// arrivée ici toutes les grandeurs évoluées de la fonction sont connues
|
|
|
|
// 2) on s'occupe maintenant des grandeurs quelconques autres qu'évoluées
|
|
const Tableau <EnumTypeQuelconque>& tqi = permet_affich_loi_nD->Tab_enu_quelconque();
|
|
Valeurs_quelconque_interpoler_ou_calculer
|
|
(absolue,TEMPS_tdt,tqi,li_quelconque,NULL,NULL,NULL,NULL);
|
|
|
|
// calcul de la valeur et retour dans tab_ret
|
|
Tableau <double> & tab_val
|
|
= permet_affich_loi_nD->Valeur_FnD_Evoluee(&val_ddl_enum,&li_enu_scal,&li_quelc,&tab_pt_li_quelconque,NULL);
|
|
#ifdef MISE_AU_POINT
|
|
if (tab_val.Taille() != 1)
|
|
{ cout << "\nErreur : la fonction nD relative a l'affichage dans la loi de comportement "
|
|
<< " doit calculer un vecteur de dimention 1 or le tableau de retour est de taille "
|
|
<< tab_val.Taille() << " ce n'est pas normal !\n";
|
|
cout << " Loi_comp_abstraite::Cal_permet_affichage()\n";
|
|
Sortie(1);
|
|
};
|
|
#endif
|
|
// on récupère les valeurs du tableau
|
|
permet_affich_loi= tab_val(1);
|
|
// retour
|
|
return permet_affich_loi;
|
|
};
|
|
|
|
// sortie du niveau d'affichage
|
|
void Loi_comp_abstraite::Affiche_niveau_affichage()const
|
|
{ cout << " niveau_affichage_local= ";
|
|
if (permet_affich_loi_nD == NULL)
|
|
{ cout << permet_affich_loi; }
|
|
else
|
|
{ cout << " controle via la fonction nD: "<< permet_affich_loi_nD->NomFonction()
|
|
<< " (derniere valeur: "<<permet_affich_loi << ") ";
|
|
};
|
|
};
|
|
|
|
|
|
void Loi_comp_abstraite::Affiche_niveau_affichage(ofstream& sort,const int cas)
|
|
{ // on traite en fonction de l'existance ou non d'une fonction nD
|
|
if (permet_affich_loi_nD != NULL)
|
|
{sort << " 1 permet_affich_loi_nD: ";
|
|
LesFonctions_nD::Ecriture_pour_base_info(sort,cas,permet_affich_loi_nD);
|
|
}
|
|
else
|
|
{sort << " 0 " << permet_affich_loi ; };
|
|
};
|
|
void Loi_comp_abstraite::Lecture_permet_affichage
|
|
(ifstream& ent,const int cas,LesFonctions_nD& lesFonctionsnD)
|
|
{
|
|
// on traite en fonction de l'existance ou non d'une fonction nD
|
|
int test =0;string nom;
|
|
ent >> test;
|
|
if (test)
|
|
{ent >> nom;
|
|
if (nom != " permet_affich_loi_nD: ")
|
|
{ cout << "\n erreur en lecture de la fonction nD, on attendait "
|
|
<< " permet_affich_loi_nD: et on a lue " << nom
|
|
<< "\n Loi_comp_abstraite::Lecture_permet_affichage(...";
|
|
Sortie(1);
|
|
};
|
|
|
|
permet_affich_loi_nD = lesFonctionsnD.Lecture_pour_base_info
|
|
( ent,cas,permet_affich_loi_nD);
|
|
}
|
|
else
|
|
{ent >> permet_affich_loi;
|
|
if (permet_affich_loi_nD != NULL)
|
|
if (permet_affich_loi_nD->NomFonction() == "_") delete permet_affich_loi_nD;
|
|
permet_affich_loi_nD = NULL;
|
|
};
|
|
};
|
|
|
|
// lecture de l'affichage avec éventuellement une fonction nD
|
|
void Loi_comp_abstraite::Lecture_permet_affichage(UtilLecture * entreePrinc,LesFonctions_nD& lesFonctionsnD)
|
|
{// il faut voir s'il s'agit d'un niveau paramétrée par une fonction nD ou pas
|
|
string nom_class_methode("Loi_comp_abstraite::Lecture_permet_affichage(..");
|
|
if (strstr(entreePrinc->tablcar,"affichage_fonction_nD:")!= NULL)
|
|
{ string nom;
|
|
string mot_cle2="affichage_fonction_nD:";
|
|
string nom_fonct;
|
|
bool lec = entreePrinc->Lecture_mot_cle_et_string(nom_class_methode,mot_cle2,nom_fonct);
|
|
if (!lec )
|
|
{ entreePrinc->MessageBuffer("**erreur en lecture** "+mot_cle2);
|
|
throw (UtilLecture::ErrNouvelleDonnee(-1));
|
|
Sortie(1);
|
|
};
|
|
// maintenant on définit la fonction
|
|
if (lesFonctionsnD.Existe(nom_fonct))
|
|
{permet_affich_loi_nD = lesFonctionsnD.Trouve(nom_fonct);
|
|
}
|
|
else
|
|
{// sinon il faut la lire maintenant
|
|
string non("_");
|
|
permet_affich_loi_nD = Fonction_nD::New_Fonction_nD(non, Id_Nom_Fonction_nD(nom_fonct));
|
|
// lecture de la courbe
|
|
permet_affich_loi_nD->LectDonnParticulieres_Fonction_nD (non,entreePrinc);
|
|
// maintenant on vérifie que la fonction est utilisable
|
|
if (permet_affich_loi_nD->NbComposante() != 1 )
|
|
{ cout << "\n erreur en lecture, la fonction " << nom_fonct
|
|
<< " est une fonction vectorielle a " << permet_affich_loi_nD->NbComposante()
|
|
<< " composante alors qu'elle devrait etre scalaire ! "
|
|
<< " elle n'est donc pas utilisable !! ";
|
|
string message("\n**erreur03** \n"+nom_class_methode+"(...");
|
|
entreePrinc->MessageBuffer(message);
|
|
throw (UtilLecture::ErrNouvelleDonnee(-1));
|
|
Sortie(1);
|
|
};
|
|
// on regarde si la fonction nD intègre la température
|
|
const Tableau <Ddl_enum_etendu>& tab_enu = permet_affich_loi_nD->Tab_enu_etendu();
|
|
if (tab_enu.Contient(TEMP))
|
|
thermo_dependant=true;
|
|
};
|
|
}
|
|
else // sinon il s'agit d'un simple entier
|
|
{*(entreePrinc->entree) >> permet_affich_loi;
|
|
// gestion du pointeur de fonction
|
|
if (permet_affich_loi_nD != NULL)
|
|
if (permet_affich_loi_nD->NomFonction() == "_")
|
|
delete permet_affich_loi_nD;
|
|
};
|
|
|
|
};
|
|
|
|
|