poisson_frontiere_double.C

00001 /*
00002  *   Copyright (c) 2000-2001 Philippe Grandclement
00003  *
00004  *   This file is part of LORENE.
00005  *
00006  *   LORENE is free software; you can redistribute it and/or modify
00007  *   it under the terms of the GNU General Public License as published by
00008  *   the Free Software Foundation; either version 2 of the License, or
00009  *   (at your option) any later version.
00010  *
00011  *   LORENE is distributed in the hope that it will be useful,
00012  *   but WITHOUT ANY WARRANTY; without even the implied warranty of
00013  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00014  *   GNU General Public License for more details.
00015  *
00016  *   You should have received a copy of the GNU General Public License
00017  *   along with LORENE; if not, write to the Free Software
00018  *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00019  *
00020  */
00021 
00022 
00023 char poisson_frontiere_double_C[] = "$Header: /cvsroot/Lorene/C++/Source/Non_class_members/PDE/poisson_frontiere_double.C,v 1.1.1.1 2001/11/20 15:19:28 e_gourgoulhon Exp $" ;
00024 
00025 /*
00026  * $Id: poisson_frontiere_double.C,v 1.1.1.1 2001/11/20 15:19:28 e_gourgoulhon Exp $
00027  * $Log: poisson_frontiere_double.C,v $
00028  * Revision 1.1.1.1  2001/11/20 15:19:28  e_gourgoulhon
00029  * LORENE
00030  *
00031  * Revision 2.1  2000/05/15  15:46:43  phil
00032  * *** empty log message ***
00033  *
00034  * Revision 2.0  2000/04/27  15:19:52  phil
00035  * *** empty log message ***
00036  *
00037  *
00038  * $Header: /cvsroot/Lorene/C++/Source/Non_class_members/PDE/poisson_frontiere_double.C,v 1.1.1.1 2001/11/20 15:19:28 e_gourgoulhon Exp $
00039  *
00040  */
00041 
00042 
00043 // Header C : 
00044 #include <stdlib.h>
00045 #include <math.h>
00046 
00047 // Headers Lorene :
00048 #include "matrice.h"
00049 #include "tbl.h"
00050 #include "mtbl_cf.h"
00051 #include "map.h"
00052 #include "base_val.h"
00053 #include "proto.h"
00054 #include "type_parite.h"
00055 #include "utilitaires.h"
00056 
00057 
00058 
00059 
00060         //----------------------------------------------
00061        //       Version Mtbl_cf
00062       //----------------------------------------------
00063 
00064 Mtbl_cf sol_poisson_frontiere_double (const Map_af& mapping, 
00065     const Mtbl_cf& source, const Mtbl_cf& lim_func, const Mtbl_cf& lim_der, 
00066                     int num_zone)
00067 
00068 {
00069     
00070     // Verifications d'usage sur les zones
00071     int nz = source.get_mg()->get_nzone() ;
00072     assert (nz>1) ;
00073     assert ((num_zone>0) && (num_zone<nz-1)) ;
00074     assert(source.get_mg()->get_type_r(num_zone) == FIN) ;
00075     
00076     assert (lim_func.get_mg() == source.get_mg()->get_angu()) ;
00077     assert (lim_der.get_mg() == source.get_mg()->get_angu()) ;
00078     assert (source.get_etat() != ETATNONDEF) ;
00079     assert (lim_func.get_etat() != ETATNONDEF) ;
00080     assert (lim_der.get_etat() != ETATNONDEF) ;
00081      
00082     // Bases spectrales
00083     const Base_val& base = source.base ;
00084     
00085     // donnees sur la zone
00086     int nr = source.get_mg()->get_nr(num_zone) ;
00087     int nt = source.get_mg()->get_nt(num_zone) ;
00088     int np = source.get_mg()->get_np(num_zone) ;;
00089     int base_r ;
00090     int l_quant, m_quant;
00091     
00092     double alpha = mapping.get_alpha()[num_zone] ;
00093     double beta = mapping.get_beta()[num_zone] ;
00094     double echelle = beta/alpha ;
00095     double facteur ;
00096     
00097     //Rangement des valeurs intermediaires 
00098     Tbl *so ;
00099     Tbl *sol_hom ;
00100     Tbl *sol_part ;
00101     Matrice *operateur ;
00102     Matrice *nondege ;
00103     
00104     
00105     Mtbl_cf resultat(source.get_mg(), base) ;
00106     resultat.annule_hard() ;
00107     
00108     for (int k=0 ; k<np+1 ; k++)
00109     for (int j=0 ; j<nt ; j++) 
00110         if (nullite_plm(j, nt, k, np, base) == 1)
00111         {
00112         // calcul des nombres quantiques :
00113         donne_lm(nz, num_zone, j, k, base, m_quant, l_quant, base_r) ;
00114         
00115         // Construction de l'operateur
00116         operateur = new Matrice(laplacien_mat
00117                     (nr, l_quant, echelle, 0, base_r)) ;
00118         
00119         (*operateur) = combinaison(*operateur, l_quant, echelle, 0, 
00120                                      base_r) ;
00121         
00122          // Operateur inversible
00123         nondege = new Matrice(prepa_nondege(*operateur, l_quant, 
00124                             echelle, 0, base_r)) ;      
00125         
00126         // Calcul DES DEUX SH
00127         sol_hom = new Tbl(solh(nr, l_quant, echelle, base_r)) ;
00128         
00129         // Calcul de la SP
00130         so = new Tbl(nr) ;
00131         so->set_etat_qcq() ;
00132         for (int i=0 ; i<nr ; i++)
00133             so->set(i) = source(num_zone, k, j, i) ;
00134         
00135         sol_part = new Tbl (solp(*operateur, *nondege, alpha,
00136                      beta, *so, 0, base_r)) ;
00137         
00138          //-------------------------------------------
00139         // On est parti pour imposer la boundary
00140         //-------------------------------------------    
00141         // Conditions de raccord type Dirichlet :
00142         // Pour la sp :
00143         double somme = 0 ;
00144         for (int i=0 ; i<nr ; i++)
00145             if (i%2 == 0)
00146             somme += (*sol_part)(i) ;
00147             else
00148             somme -= (*sol_part)(i) ;
00149             
00150             facteur = (lim_func(num_zone-1, k, j, 0)-somme)
00151                 * pow(echelle-1, l_quant+1) ;
00152             
00153             for (int i=0 ; i<nr ; i++)
00154             sol_part->set(i) +=
00155                 facteur*(*sol_hom)(1, i) ;
00156             
00157             // pour l'autre solution homogene :
00158             facteur = - pow(echelle-1, 2*l_quant+1) ;
00159             for (int i=0 ; i<nr ; i++)
00160             sol_hom->set(0, i) +=
00161                 facteur*(*sol_hom)(1, i) ;
00162             
00163             // Condition de raccord de type Neumann :
00164             double val_der_solp = 0 ;
00165             for (int i=0 ; i<nr ; i++)
00166             if (i%2 == 0)
00167                 val_der_solp -= i*i*(*sol_part)(i)/alpha ;
00168             else
00169                 val_der_solp += i*i*(*sol_part)(i)/alpha ;
00170             
00171             double val_der_solh = 0 ;
00172             for (int i=0 ; i<nr ; i++)
00173             if (i%2 == 0)
00174                 val_der_solh -= i*i*(*sol_hom)(0, i)/alpha ;
00175             else
00176                 val_der_solh += i*i*(*sol_hom)(0, i)/alpha ;
00177             
00178             assert (val_der_solh != 0) ;
00179                 
00180             facteur = (lim_der(num_zone-1, k, j, 0)-val_der_solp) /
00181                 val_der_solh ;
00182             
00183             for (int i=0 ; i<nr ; i++)
00184             sol_part->set(i) +=
00185                 facteur*(*sol_hom)(0, i) ;
00186             
00187             // solp contient le bon truc (normalement ...)
00188             for (int i=0 ; i<nr ; i++)
00189             resultat.set(num_zone, k, j, i) = (*sol_part)(i) ;
00190             
00191         delete operateur ;
00192         delete nondege ;
00193         delete so ;
00194         delete sol_hom ;
00195         delete sol_part ;
00196         }
00197     return resultat ;
00198 }

Generated on Tue Feb 7 01:35:19 2012 for LORENE by  doxygen 1.4.6