// fichier: Base.h
// 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) .
//
// Herezh++ is distributed under GPL 3 license ou ultérieure.
//
// Copyright (C) 1997-2022 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 .
//
// For more information, please consult: .
/************************************************************************
* DATE: 23/01/97 *
* $ *
* AUTEUR: G RIO *
* $ *
* PROJET: Herezh++ *
* $ *
************************************************************************
* BUT: Les classes Base servent à définir des bases en 1D 2D 3D
* qui permettent d'exprimer des coordonnées, en absolue ou en locale.
* Ces bases correspondent à des bases naturelles ou des bases duales.
* $ *
* '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' *
* MODIFICATIONS: *
* ! date ! auteur ! but ! *
* ------------------------------------------------------------ *
* $ *
************************************************************************/
#ifndef BASE_H
#define BASE_H
#include "Tableau_T.h"
#include "Coordonnee1.h"
#include "Mat_pleine.h"
/** @defgroup Les_classes_Base
*
* BUT: Les classes Base servent à définir des bases en 1D 2D 3D
* qui permettent d'exprimer des coordonnées, en absolue ou en locale.
* Ces bases correspondent à des bases naturelles ou des bases duales.
* \author Gérard Rio
* \version 1.0
* \date 23/01/97
* \brief Définition des bases naturelles ou absolues,
* ou des bases duales.
*
*/
/// @addtogroup Les_classes_Base
/// @{
///
class BaseH;
class Util;
//===============================================================
//! Les base covariantes et absolus
//===============================================================
class BaseB
{ /// surcharge de l'operator de lecture avec le type
friend istream & operator >> (istream &, BaseB &);
/// surcharge de l'operator d'ecriture
friend ostream & operator << (ostream &, const BaseB &);
public :
// VARIABLES PUBLIQUES :
// CONSTRUCTEURS :
/*! \brief
// constructeur par defaut, defini la Base absolu en dimension 3
// les vecteurs sont unitaires, ex en dim 2 ->
// la base : 1,0 et 0,1 */
BaseB () ;
/// defini la Base absolu en dimension dim
BaseB (int dim);
/*! \brief
// defini une Base relative v1(dim)
// c-a-d differente de la base triviale absolu */
BaseB (int dim, const Tableau & v1);
/*! \brief
// defini une Base locale absolue (triviale) de n vecteurs
// de dimension dim */
BaseB (int dim,int n);
/// idem dessus mais avec toutes les composantes = s
BaseB (int dim,int n,double s);
/*! \brief
// defini une Base locale relative v1(dim)
// de n vecteurs de dimension dim */
BaseB (int dim,int n,const Tableau & v1);
/// constructeur de copie
BaseB (const BaseB &) ;
/// DESTRUCTEUR :
~BaseB ();
// METHODES PUBLIQUES :
/// surcharge de l'affectation
BaseB & operator = (const BaseB & aB);
// retourne la dimension des vecteurs
inline const int Dimension () const
{return dimension; };
/// retourne le nombre de vecteurs de la base
inline const int NbVecteur () const
{return nb_vecteur; };
/// retourne le i ieme vecteurs en lecture only
const CoordonneeB & operator () (int i) const;
/// retourne le i ieme vecteurs en I/O
CoordonneeB& CoordoB(int i) ;
/// acces directe contrôlé à des vecteurs sans variance: uniquement en lecture
const Coordonnee & Coordo(int i) const ;
/// affichage à l'écran des infos
void Affiche() const;
/*! \brief
// affectation trans_variance: utile pour une recopie de mêmes valeurs
// mais ici l'appel est explicite donc a priori on sait ce que l'on fait
// il n'y a pas de redimensionnement, donc la dimension et le nombre des vecteurs
// doivent être identiques */
void Affectation_trans_variance(const BaseH& aH);
/*! \brief
// changement de base
// on suppose que this(i) correspond aux coordonnées dans un premier repère I_a
// IpH correspond aux coordonnées dans I_a d'un nouveau repère
// en sortie: apB(i) correspond aux coordonnées dans ipB de this(i) */
void Change_repere(const BaseH& IpH, BaseB& apB);
/*! \brief
// la méthode qui suit a pour objectif de calculer les vecteurs de la base naturelle finale
// associée à un paramétrage cartésien initial */
/// donc soit connue une base naturelle \hat g_i associée à un paramétrage theta^i
/// \hat g_i est représenté par les vecteurs de this, et représente la situation déformée
/// soit la base duale de g_i : gammaH^i = g^i c-à-d la base duale en situation non déformée
/// maintenant: si on considère les coordonnées initiales X^i on cherche
/// les vecteurs des bases naturelles associées à X^i avant g'_i et après déformation \hat g'_i
/// \n on a (cf. annexe dans le document théorique d'Herezh)
/// \n g'_i = I_i par définition et
/// \n \hat g'_i = (\vec I_i . \vec g^j) ~\hat g_j c-a-d
/// \n \hat g'_i = gammaH^j(i) * (*this)(j)
/// \n c'est le résultat de la méthode qui suit
/// \n changement de base: retourne apB(a) = (*this)(j) . gamma^j_a
/// il faut que le nombre de vecteur de apB soit identique à la dimension de gammaH
/// et que le nombre de vecteur de gammaH soit identique au nombre de vecteur de this
/// et que la dimension de apB soit identique à la dimension de this
void ChangeBase_theta_vers_Xi(BaseB& apB, const BaseH& gammaH);
/*! \brief
// la méthode calcule à partir de this qui correspond à g_alpha dans I_a:
// apB : g_alpha dans I'^alpha
// apH : g^alpha dans I'^alpha
// IpB : I'_beta dans I_a */
/// soient une base globale orthonormée : I_a et une base locale orthonormée I'_alpha
/// pour l'instant: I_a est en 3 dimensions et alpha varie de 1 à 2
/// soient une base naturelle g_alpha et duale associée g^beta
/// telles que : I'_alpha appartient à l'espace des g_alpha ou g^beta
/// \n A) on a:
/// g^alpha = gamma(alpha,beta) * I'^beta c-a-d : gamma^alpha_beta
/// \n NB: 1) comme I'est orthonormée: I'^beta = I'_beta
/// \n 2) chaque ligne de gamma représente un g^alpha
/// \n B) dans ce contexte on a:
/// inverse de gamma -> une matrice beta et chaque ligne de beta représente
/// les coordonnées de g_alpha dans I'^alpha
/// c-a-d g_alpha = alpha (delta,alpha) * I'_delta
/// \n C) on peut également calculer les coordonnées de I'_beta dans le repère globale
/// \n I'_beta = gamma(alpha,beta) * g_alpha
//
void ChangeBase_curviligne( const Mat_pleine& gamma, BaseB& apB , BaseH& apH, BaseB& IpB ) const;
/*! \brief
// calcul des composantes de coordonnées locales dans la base absolue
// en argument : A -> une reference sur les coordonnées résultat qui peut avoir une dimension
// différente des coordonnées locale, retour d'une reference sur A */
Coordonnee & BaseAbsolue(Coordonnee & A,const CoordonneeH & B) const;
/*! \brief
// une partie des vecteurs de B est affectée à this,
// si this contient plus de vecteur que B, les autres vecteurs sont mis à 0 ou non
// suivant la valeur de plusZero: = false: les autres vecteurs sont inchangées,
// plusZero = true: les autres vecteurs sont mis à 0 */
void Affectation_partielle(int nb_vecteur_a_affecter, const BaseB & B,bool plusZero);
private :
// VARIABLES PROTEGEES :
int dimension; // dimension des vecteurs de la Base
int nb_vecteur; // nombre de vecteur de la base
Tableau v ; // pointeur des vecteurs covariants de la Base
Tableau v_sans ; // pointeur des vecteurs sans variance de la Base
/// on met à la même place les v_sans que les v
void Meme_place_coordonnee();
};
/// @} // end of group
/// @addtogroup Les_classes_Base
/// @{
///
//===============================================================
//! Les base duales
//===============================================================
class BaseH
{ /// surcharge de l'operator de lecture avec le type
friend istream & operator >> (istream &, BaseH &);
/// surcharge de l'operator d'ecriture
friend ostream & operator << (ostream &, const BaseH &);
public :
// VARIABLES PUBLIQUES :
// CONSTRUCTEURS :
/*! \brief
// par defaut, defini une Base absolu en dimension 3
// les vecteurs sont unitaires, ex en dim 2 ->
// la base : 1,0 et 0,1 */
BaseH () ;
/// defini une Base absolu en dimension dim
BaseH (int dim);
/*! \brief
// defini une Base relative v1(dim)
// c-a-d differente de la base triviale absolue */
BaseH (int dim, const Tableau & v1);
/*! \brief
// defini une Base locale absolue (triviale) de n vecteurs
// de dimension dim */
BaseH (int dim,int n);
/// idem dessus mais avec toutes les composantes = s
BaseH (int dim,int n,double s);
/// defini une Base locale relative v1(dim) de n vecteurs de dimension dim
BaseH (int dim,int n,const Tableau& v1);
/// constructeur de copie
BaseH (const BaseH &) ;
/// DESTRUCTEUR :
~BaseH ();
// METHODES PUBLIQUES :
/// surcharge de l'affectation
BaseH & operator = (const BaseH & aB);
/// retourne la dimension des vecteurs
inline const int Dimension () const
{return dimension; };
/// retourne le nombre de vecteurs de la base
inline const int NbVecteur () const
{return nb_vecteur; };
/// retourne le i ieme vecteurs en lecture only
const CoordonneeH & operator () (int i) const;
/// retourne le i ieme vecteurs en I/O
CoordonneeH& CoordoH(int i) ;
/// acces directe contrôlé à des vecteurs sans variance: uniquement en lecture
const Coordonnee & Coordo(int i) const ;
/// affichage à l'écran des infos
void Affiche() const;
/*! \brief
// affectation trans_variance: utile pour une recopie de mêmes valeurs
// mais ici l'appel est explicite donc a priori on sait ce que l'on fait
// il n'y a pas de redimensionnement, donc la dimension et le nombre des vecteurs
// doivent être identiques */
void Affectation_trans_variance(const BaseB& aB);
/*! \brief
// changement de base
// on suppose que this(i) correspond aux coordonnées dans un premier repère I_a
// IpB correspond aux coordonnées dans I_a d'un nouveau repère
// en sortie: apH(i) correspond aux coordonnées dans ipH de this(i) */
void Change_repere(const BaseB& IpB, BaseH& apH);
/*! \brief
// la méthode qui suit a pour objectif de calcul les vecteurs de la base naturelle finale
// associée à un paramétrage cartésien initiale */
/// donc soit connue une base duale \hat g^i associée à un paramétrage theta^i
/// \hat g^i est représenté par les vecteurs de this, et représente la situation déformée
/// soit la base naturel de g_i : betaB_i = g_i c-à-d la base naturelle en situation non déformée
/// maintenant: si on considère les coordonnées initiales X^i on cherche
/// les vecteurs des bases duales associées à X^i avant g'^i et après déformation \hat g'^i
/// on a (cf. annexe dans le document théorique d'Herezh)
/// \n g'^i = g'_i = I_i = I^i par définition et
/// \n \hat g'^i = (\vec I_i . \vec g_j) ~\hat g^j c-a-d
/// \n \hat g'^i = betaB^j(i) * (*this)(j)
/// \n c'est le résultat de la méthode qui suit
/// \n changement de base: retourne apH(a) = (*this)(j) . beta_j^a
/// il faut que le nombre de vecteur de apH soit identique à la dimension de betaB
/// et que le nombre de vecteur de betaB soit identique au nombre de vecteur de this
/// et que la dimension de apB soit identique à la dimension de this
void ChangeBase_theta_vers_Xi(BaseH& apH, const BaseB& betaB);
/*! \brief
// la méthode calcule à partir de this qui correspond à g^alpha dans I_a:
// apB : g_alpha dans I'^alpha
// apH : g^alpha dans I'^alpha
// IpH : I'^beta dans I_a */
/// soient une base globale orthonormée : I_a et une base locale orthonormée I'_alpha
/// pour l'instant: I_a est en 3 dimensions et alpha varie de 1 à 2
/// soient une base naturelle g_alpha et duale associée g^beta
/// telles que : I'_alpha appartient à l'espace des g_alpha ou g^beta
/// \n A) on a:
/// g^alpha = gamma(alpha,beta) * I'^beta c-a-d : gamma^alpha_beta
/// \n NB: 1) comme I'est orthonormée: I'^beta = I'_beta
/// 2) chaque ligne de gamma représente un g^alpha
/// \n B) dans ce contexte on a:
/// inverse de gamma -> une matrice beta et chaque ligne de beta représente
/// les coordonnées de g_alpha dans I'^alpha
/// c-a-d g_alpha = alpha (delta,alpha) * I'_delta
/// \n C) on peut également calculer les coordonnées de I'_beta dans le repère globale
/// \n I'_beta = gamma(alpha,beta) * g_alpha
//
void ChangeBase_curviligne( const Mat_pleine& gamma, BaseB& apB , BaseH& apH, BaseH& IpH ) const;
/*! \brief
// calcul des composantes de coordonnées locales dans la base absolue
// en argument : A -> une reference sur les coordonnées résultat qui peut avoir une dimension
// différente des coordonnées locale, retour d'une reference sur A */
Coordonnee & BaseAbsolue(Coordonnee & A,const CoordonneeB & B) const;
/*! \brief
// une partie des vecteurs de B est affectée à this,
// si this contient plus de vecteur que B, les autres vecteurs sont mis à 0 ou non
// suivant la valeur de plusZero: = false: les autres vecteurs sont inchangées,
// plusZero = true: les autres vecteurs sont mis à 0 */
void Affectation_partielle(int nb_vecteur_a_affecter, const BaseH & B,bool plusZero);
private :
// VARIABLES PROTEGEES :
int dimension; // dimension des vecteurs de la Base
int nb_vecteur; // nombre de vecteur de la base
Tableau v ; // pointeur des vecteurs contravariant de la Base
Tableau v_sans ; // pointeur des vecteurs sans variance de la Base
// on met à la même place les v_sans que les v
void Meme_place_coordonnee();
};
/// @} // end of group
/// @addtogroup Les_classes_Base
/// @{
//=========================================================================
//! un groupe de 3 bases covariantes et absolus à 0, t et tdt
//=========================================================================
/// il s'agit ici essentiellement d'un conteneur pour optimiser le stockage
//=========================================================================
class BaseB_0_t_tdt
{ /// surcharge de l'operator de lecture avec le type
friend istream & operator >> (istream &, BaseB_0_t_tdt &);
/// surcharge de l'operator d'ecriture
friend ostream & operator << (ostream &, const BaseB_0_t_tdt &);
public :
// VARIABLES PUBLIQUES :
// CONSTRUCTEURS :
/// par defaut, defini les Bases en absolu en dimension 3
/// les vecteurs sont unitaires, ex en dim 2 ->
/// la base : 1,0 et 0,1
BaseB_0_t_tdt () :
baseB_0(),baseB_t(), baseB() {};
/// defini les Bases en absolu en dimension dim
BaseB_0_t_tdt (int dim) :
baseB_0(dim),baseB_t(dim), baseB(dim) {};
/// defini 3 Bases relatives v1(dim)
/// c-a-d differente de la base triviale absolu
BaseB_0_t_tdt (int dim, const Tableau & v1) :
baseB_0(dim,v1),baseB_t(dim,v1), baseB(dim,v1) {};
/// defini les Bases locale absolue (triviale) de n vecteurs
/// de dimension dim
BaseB_0_t_tdt (int dim,int n) :
baseB_0(dim,n),baseB_t(dim,n), baseB(dim,n) {};
/// idem dessus mais avec toutes les composantes = s
BaseB_0_t_tdt (int dim,int n,double s) :
baseB_0(dim,n,s),baseB_t(dim,n,s), baseB(dim,n,s) {};
/// defini les Bases locale relative v1(dim)
/// de n vecteurs de dimension dim
BaseB_0_t_tdt (int dim,int n,const Tableau & v1) :
baseB_0(dim,n,v1),baseB_t(dim,n,v1), baseB(dim,n,v1) {};
/// constructeur de copie
BaseB_0_t_tdt (const BaseB_0_t_tdt & b):
baseB_0(b.baseB_0),baseB_t(b.baseB_t), baseB(b.baseB) {};
/// DESTRUCTEUR :
~BaseB_0_t_tdt () {};
// METHODES PUBLIQUES :
/// surcharge de l'affectation
BaseB_0_t_tdt & operator = (const BaseB_0_t_tdt & b)
{baseB_0 = b.baseB_0; baseB_t = b.baseB_t; baseB = b.baseB;return *this;
};
/// récupération de la base,
/// a) en constant, la base actuelle
const BaseB& Const_BaseB_Noeud() const {return baseB;};
/// b) en constant, la base à t
const BaseB& Const_BaseB_Noeud_t() const {return baseB_t;};
/// c) en constant, la base initiale
const BaseB& Const_BaseB_Noeud_0() const {return baseB_0;};
/// d) en lecture écriture, la base actuelle
BaseB& BaseB_Noeud() {return baseB;};
/// e) en lecture écriture, la base à t
BaseB& BaseB_Noeud_t() {return baseB_t;};
/// f) en lecture écriture, la base à 0
BaseB& BaseB_Noeud_0() {return baseB_0;};
private :
BaseB baseB_0; // à 0
BaseB baseB_t; // à t
BaseB baseB; // actuelle
};
/// @} // end of group
/// @addtogroup Les_classes_Base
/// @{
///
//=========================================================================
//! un groupe de 3 bases contravariant et absolus à 0, t et tdt
//=========================================================================
/// il s'agit ici essentiellement d'un conteneur pour optimiser le stockage
//=========================================================================
class BaseH_0_t_tdt
{ /// surcharge de l'operator de lecture avec le type
friend istream & operator >> (istream & ent, BaseH_0_t_tdt &)
{ cout << "\n *** operateur non implante !! "
<< " friend istream & operator ecriture ";
Sortie(1);
return ent;
};
/// surcharge de l'operator d'ecriture
friend ostream & operator << (ostream & sort, const BaseH_0_t_tdt &);
public :
// VARIABLES PUBLIQUES :
/// CONSTRUCTEURS :
/// par defaut, defini les Bases en absolu en dimension 3
/// les vecteurs sont unitaires, ex en dim 2 ->
/// la base : 1,0 et 0,1
BaseH_0_t_tdt () :
baseH_0(),baseH_t(), baseH() {};
/// defini les Bases en absolu en dimension dim
BaseH_0_t_tdt (int dim) :
baseH_0(dim),baseH_t(dim), baseH(dim) {};
/// defini 3 Bases relatives v1(dim)
/// c-a-d differente de la base triviale absolu
BaseH_0_t_tdt (int dim, const Tableau & v1) :
baseH_0(dim,v1),baseH_t(dim,v1), baseH(dim,v1) {};
/// defini les Bases locale absolue (triviale) de n vecteurs
/// de dimension dim
BaseH_0_t_tdt (int dim,int n) :
baseH_0(dim,n),baseH_t(dim,n), baseH(dim,n) {};
/// idem dessus mais avec toutes les composantes = s
BaseH_0_t_tdt (int dim,int n,double s) :
baseH_0(dim,n,s),baseH_t(dim,n,s), baseH(dim,n,s) {};
/// defini les Bases locale relative v1(dim)
/// de n vecteurs de dimension dim
BaseH_0_t_tdt (int dim,int n,const Tableau & v1) :
baseH_0(dim,n,v1),baseH_t(dim,n,v1), baseH(dim,n,v1) {};
/// constructeur de copie
BaseH_0_t_tdt (const BaseH_0_t_tdt & b):
baseH_0(b.baseH_0),baseH_t(b.baseH_t), baseH(b.baseH) {};
/// DESTRUCTEUR :
~BaseH_0_t_tdt () {};
// METHODES PUBLIQUES :
/// surcharge de l'affectation
BaseH_0_t_tdt & operator = (const BaseH_0_t_tdt & b)
{baseH_0 = b.baseH_0; baseH_t = b.baseH_t; baseH = b.baseH; return *this;
};
/// récupération de la base,
/// a) en constant, la base actuelle
const BaseH& Const_BaseH_Noeud() const {return baseH;};
/// b) en constant, la base à t
const BaseH& Const_BaseH_Noeud_t() const {return baseH_t;};
/// c) en constant, la base initiale
const BaseH& Const_BaseH_Noeud_0() const {return baseH_0;};
/// d) en lecture écriture, la base actuelle
BaseH& BaseH_Noeud() {return baseH;};
/// e) en lecture écriture, la base à t
BaseH& BaseH_Noeud_t() {return baseH_t;};
/// f) en lecture écriture, la base à 0
BaseH& BaseH_Noeud_0() {return baseH_0;};
private :
BaseH baseH_0; // à 0
BaseH baseH_t; // à t
BaseH baseH; // actuelle
};
/// @} // end of group
#ifndef MISE_AU_POINT
#include "Base.cc"
#define BASE_HetB_deja_inclus
#endif
#endif