TrioCFD 1.9.9_beta
TrioCFD documentation
Loading...
Searching...
No Matches
Echange_contact_VDF_FT_Disc.cpp
1/****************************************************************************
2* Copyright (c) 2015 - 2016, CEA
3* All rights reserved.
4*
5* Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
6* 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
7* 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
8* 3. Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.
9*
10* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
11* IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
12* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
13*
14*****************************************************************************/
15
16#include <Echange_contact_VDF_FT_Disc.h>
17
18#include <Champ_front_calc.h>
19#include <Probleme_base.h>
20#include <Champ_Uniforme.h>
21#include <Schema_Temps_base.h>
22#include <Milieu_base.h>
23#include <Modele_turbulence_scal_base.h>
24#include <Domaine_VDF.h>
25#include <Equation_base.h>
26#include <Conduction.h>
27#include <Param.h>
28#include <Probleme_FT_Disc_gen.h>
29#include <Triple_Line_Model_FT_Disc.h>
30#include <Domaine_VF.h>
31#include <Front_VF.h>
32
33
34// XD paroi_echange_contact_vdf_ft paroi_echange_contact_vdf paroi_echange_contact_vdf_ft INHERITS_BRACE This boundary
35// XD_CONT condition is used between a conduction problem and a thermohydraulic problem with two phases flow
36// XD_CONT (Front-Tracking method) to modelize heat exchange.
37Implemente_instanciable( Echange_contact_VDF_FT_Disc, "Echange_contact_VDF_FT_Disc", Echange_contact_VDF ) ;
38// XD echange_contact_vdf_ft_disc condlim_base echange_contact_vdf_ft_disc BRACE echange_conatct_vdf en prescisant la
39// XD_CONT phase
40
42{
44 return os;
45}
46
48{
49 if (app_domains.size() == 0) app_domains = { Motcle("Thermique") };
50
51 // Echange_contact_VDF::readOn( is );
52 Cerr<<"Lecture des parametres du contact (Echange_contact_VDF_FT_Disc::readOn)"<<finl;
53 Param param("Echange_contact_VDF_FT_Disc::readOn");
54 param.ajouter("autre_probleme",&nom_autre_pb_,Param::REQUIRED); // XD_ADD_P chaine
55 // XD_CONT name of other problem
56 param.ajouter("autre_bord",&nom_bord,Param::REQUIRED); // XD_ADD_P chaine
57 // XD_CONT name of other boundary
58 param.ajouter("autre_champ_temperature",&nom_champ,Param::REQUIRED); // XD_ADD_P chaine
59 // XD_CONT name of other field
60 param.ajouter("nom_mon_indicatrice",&nom_champ_indicatrice_,Param::REQUIRED); // XD_ADD_P chaine
61 // XD_CONT name of indicatrice
62 param.ajouter("Ri_liq",&Ri_); // XD_ADD_P double
63 // XD_CONT interficial thermal resitence of liquid
64 int phase = INT_MAX; // should be overriden after reading. see next line
65 param.ajouter("phase",&phase,Param::REQUIRED); // XD_ADD_P int
66 // XD_CONT phase
67 param.lire_avec_accolades(s);
68 indicatrice_ref_ = double(phase);
70
71 h_paroi=1e10; // why not git 1/h_paroi = 0....?
72 // T_autre_pb(): temp type front from other calculation/OWN_PTR(Champ_base) dans le domaine
73 T_autre_pb_.typer("Champ_front_calc");
74 // T_ext(): mettre_a_jour utilise des donnees externes,
75 // Peut aussi initialized by a champ dans le domaine.
76 le_champ_front.typer("Ch_front_var_instationnaire_dep");
78
79 return s;
80}
82{
83 // Champ_front_calc:: mettre_a_jour()
84 // par default distant_= 1
85 // trace the value corresponding from champ inconnu
86 // Champ_Inc_P0_base::trace(), trace the element from distant
88 indicatrice_->mettre_a_jour(temps);
89
90 const DoubleTab& I = indicatrice_->valeurs_au_temps(temps);
91
93 // le_milieu = SOLID
94 const Milieu_base& le_milieu=ch.milieu();
95 int nb_comp = le_milieu.conductivite().nb_comp();
96 assert(nb_comp==1);
97
98
99 int is_pb_fluide=0;
100
101
102 DoubleTab& mon_h= h_imp_->valeurs();
103 int opt=0;
104 calculer_h_autre_pb( autre_h, 0., opt);
105 // Here, compute h_diff in the fluid side
106 calculer_h_mon_pb(mon_h,Ri_,opt);
107
108 // juste acceder la valeur..., et les remplir
109 // pas forcement des chose dedans et valable.
110 DoubleTab& mon_Tex= T_ext(). valeurs();
111 calculer_Teta_equiv(mon_Tex,mon_h,autre_h,is_pb_fluide,temps);
112
113 // Attention: Ti_wall_ should be updated after TCL model
114 // AS it will be used in TCL model, in particular,
115 // influence the heat flux in MESO zone
116 // OK here: TCL model is called in UpdateField
117 DoubleTab& mon_Ti= Ti_wall_-> valeurs();
118 DoubleTab Twalltmp(mon_Ti);
119 Twalltmp.detach_vect();
120 calculer_Teta_paroi(Twalltmp,mon_h,autre_h,is_pb_fluide,temps);
121
122 int taille=mon_h.dimension(0);
123
124 for (int ii=0; ii<taille; ii++)
125 for (int jj=0; jj<nb_comp; jj++)
126 {
127 if (est_egal(I(ii,0),indicatrice_ref_))
128 {
129 mon_h(ii,jj)=1./(1./autre_h(ii,jj)+1./mon_h(ii,jj));
130 mon_Ti(ii, jj) = Twalltmp(ii, jj);
131 }
132 else
133 {
134 // Using Ghost Fluid Method, mon_h and T in pure-L/pure-G cells are NO-PHYSICAL
135 // the BC here are not important
136 // Setting mon_h = 0 => isothermal BC
137 mon_h(ii,jj) = 0.;
138 // Update mon_Ti in the same way (to have a good convergence)
139 mon_Ti(ii, jj) = Twalltmp(ii, jj);
140 }
141 }
142
143
144 Nom nom_pb=mon_dom_cl_dis->equation().probleme().le_nom();
145 Probleme_base& pb_gen=ref_cast(Probleme_base, Interprete::objet(nom_pb));
146 Probleme_FT_Disc_gen *pbft = dynamic_cast<Probleme_FT_Disc_gen*>(&pb_gen);
147
148 const Domaine_VF& le_dom=ref_cast(Domaine_VF, mon_dom_cl_dis -> domaine_dis());
149 const DoubleVect& surface= le_dom.face_surfaces();
150
151
152 if (pbft-> tcl().is_activated())
153 {
154
155 // phi_ext_ used in *Eval_Diff_VDF_Elem_Gen.tpp* L97
156 DoubleTab& mon_phi = phi_ext_-> valeurs();
157 mon_phi = 0;
158// **************************************To be implemented*******************
159 // 2 - phase cells at pb-Boundary when solving T-eq at Liquid side
160 //mixed mesh => Text, Twall, mon_h
161 if (indicatrice_ref_ == 1)
162 {
163 Triple_Line_Model_FT_Disc *tcl = pbft ? &pbft->tcl() : nullptr;
164 const ArrOfDouble& Q_from_CL = tcl->Q();
165 const ArrOfInt& faces_with_CL_contrib = tcl-> boundary_faces();
166 const IntTab& face_voisins = le_dom.face_voisins();
167
168
169 const int nb_contact_line_contribution = faces_with_CL_contrib.size_array();
170
171
172 for (int jj = 0; jj < nb_comp; jj++)
173 {
174 // In case of parallelization:
175 // raccord in liquid domain and faces_with_CL_contrib are in the same processeur
176 // => have the same face Number in the same position
177 // use face number to check correspondence
178 // fill mon_phi
179 for (int idx = 0; idx < nb_contact_line_contribution; idx++)
180 {
181 const int facei = faces_with_CL_contrib[idx];
182 bool Not_find_ = true;
183
184 int ii;
185 for (ii=0; ii<taille; ii++)
186 {
187 const int face = ii + frontiere_dis ().frontiere ().num_premiere_face ();
188 if (facei == face)
189 {
190 Not_find_ = false;
191 break;
192 }
193 }
194
195 const double sign = (face_voisins (facei, 0) == -1) ? -1. : 1.;
196 const double TCL_wall_flux = Q_from_CL[idx] / surface (facei);
197 const double val = -sign * TCL_wall_flux;
198
199 if (!Not_find_)
200 mon_phi(ii, jj) += val;
201 else
202 Process::exit(Nom("Echange_contact_VDF_FT_Disc : missing element corresponding") + Nom(facei) + " ! Check all faces number in TCL are at BC?" );
203 }
204
205 // replace mon_h and mon_Ti;
206 for (int ii=0; ii<taille; ii++)
207 {
208 if (!est_egal(mon_phi(ii, jj), 0.))
209 {
210 mon_Ti(ii, jj) = T_ext().valeurs()(ii, jj) - mon_phi(ii, jj) /autre_h(ii) ;
211 mon_h(ii,jj) = 0.;
212 }
213 }
214 }
215 }
216 }
217
218 // put in the end: to make sure to update the *modified* h_imp_, phi_ext_, and T_ext
221 mon_Ti.echange_espace_virtuel();
222 Ti_wall_->mettre_a_jour(temps);
223
224
225 // check if to inject a new nuclateion seed
226 // only check in the liquid - equation
227
228 if ((pbft->tcl ().reinjection_tcl ()) && (indicatrice_ref_ == 1) )
229 {
230 bool& ready_inject = pbft->tcl ().ready_inject_tcl ();
231 ready_inject = false;
232
233 int BC_has_tcl = 0;
234
235 for (int ii = 0; ii < taille; ii++)
236 if (!est_egal (I (ii, 0), indicatrice_ref_))
237 {
238 BC_has_tcl = 1;
239 break;
240 }
241 BC_has_tcl = Process::mp_max (BC_has_tcl);
242
243 if (BC_has_tcl == 0)
244 {
245 double sum_T = 0;
246 double sum_surface = 0;
247
248 for (int ii = 0; ii < taille; ii++)
249 {
250 const int face = ii
252 if (le_dom.xv (face, 0) <= pbft->tcl ().Rc_inject ())
253 {
254 sum_surface += surface (face);
255 sum_T += surface (face) * mon_Ti (ii, 0);
256 }
257 }
258
259 sum_T = Process::mp_sum (sum_T);
260 sum_surface = Process::mp_sum (sum_surface);
261
262 sum_T = (sum_surface > DMINFLOAT) ? sum_T / sum_surface : 0;
263
264 ready_inject = (sum_T >= pbft->tcl ().tempC_tcl ()) ? true : false;
265 }
266
267 ready_inject = Process::mp_max ((int)ready_inject);
268 }
269
270}
271
273{
275
276 indicatrice_.typer("Champ_front_calc");
277 Champ_front_calc& ch=ref_cast(Champ_front_calc, indicatrice_.valeur());
278
279 Nom nom_bord_=frontiere_dis().frontiere().le_nom();
280 Nom nom_pb = mon_dom_cl_dis->equation ().probleme ().le_nom ();
281
282 int distant=0;
283 // when solving pure condution pb for solid
284 if (sub_type(Conduction,domaine_Cl_dis().equation()))
285 {
286 nom_pb=nom_autre_pb_;
287 nom_bord_=nom_bord_oppose_;
288 distant=1;
289 }
290 // check the coherance and fixer nb of component
291 ch.creer(nom_pb, nom_bord_, nom_champ_indicatrice_);
292 // changer distant = 0; for indicatrice_...
293 // par default, 1;
294 ch.set_distant(distant);
296 ch.completer();
298 ch.fixer_nb_valeurs_temporelles(nb_cases);
299
300 Probleme_base& pb_gen = ref_cast(Probleme_base, Interprete::objet (nom_pb));
301
302 //ONCE phi_ext_lu_ true, will be completer in father classes
303
304 const Probleme_FT_Disc_gen *pbft =
305 dynamic_cast<const Probleme_FT_Disc_gen*> (&pb_gen);
306
307 int nb_faces_raccord1 = frontiere_dis().frontiere().nb_faces ();
308
309 if (pbft->tcl ().is_activated () && phi_ext_lu_ == false)
310 {
311 phi_ext_lu_ = true;
312
313 derivee_phi_ext_.typer ("Champ_front_fonc");
314 derivee_phi_ext_->fixer_nb_comp (1);
315 derivee_phi_ext_->associer_fr_dis_base (frontiere_dis ());
316 derivee_phi_ext_->valeurs ().resize (nb_faces_raccord1, 1);
317
318 phi_ext_.typer ("Champ_front_fonc");
319 phi_ext_->fixer_nb_comp (1);
320 phi_ext_->associer_fr_dis_base (frontiere_dis ());
321 phi_ext_->valeurs ().resize (nb_faces_raccord1, 1);
322 }
323
324
325
326 Ti_wall_.typer ("Champ_front_fonc");
327 Ti_wall_->fixer_nb_comp (1);
328 Ti_wall_->associer_fr_dis_base (frontiere_dis ());
329 Ti_wall_->valeurs().resize (nb_faces_raccord1, 1);
330 Ti_wall_-> fixer_nb_valeurs_temporelles(nb_cases);
331
332}
333
334
335
336/*! @brief Change le i-eme temps futur de la CL.
337 *
338 */
340{
342 indicatrice_->changer_temps_futur(temps,i);
343 Ti_wall_ -> changer_temps_futur(temps,i);
344}
345
346/*! @brief Tourne la roue de la CL
347 *
348 */
350{
351 int ok=Echange_contact_VDF::avancer(temps);
352 ok = ok && indicatrice_->avancer(temps);
353 ok = ok && Ti_wall_ -> avancer(temps);
354 return ok;
355}
356
357/*! @brief Tourne la roue de la CL
358 *
359 */
361{
362 int ok=Echange_contact_VDF::reculer(temps);
363 ok = ok && indicatrice_->reculer(temps);
364 ok = ok && Ti_wall_ -> reculer(temps);
365 return ok;
366}
367
369{
370
371 // T_autre_pb is ALSO created and initialised in the following line
373 return 0;
374
375 DoubleTab& mon_Ti = Ti_wall_->valeurs ();
376
377 int is_pb_fluide = 0;
378 DoubleTab mon_h (mon_Ti);
379 DoubleTab mautre_h (mon_Ti);
380 int opt = 0;
381 calculer_h_autre_pb (mautre_h, 0., opt);
382 // Here, compute h_diffusion in the fluid side
383 calculer_h_mon_pb (mon_h, 0., opt);
384
385 // Use Twalltmp to avoid resize distributed array mon_Ti
386 // when calling calculer_Teta_paroi
387 DoubleTab Twalltmp (mon_Ti);
388 Twalltmp.detach_vect ();
389
390 calculer_Teta_paroi (Twalltmp, mon_h, mautre_h, is_pb_fluide, temps);
391
392 // Echange_contact_VDF initilise T as temp of liq
393 // some pb in initilization of Twall
394 // T_autre_pb().mettre_a_jour(temps);
395
396 int taille = mon_Ti.dimension (0);
397 for (int ii = 0; ii < taille; ii++)
398 {
399 double tempValue = Twalltmp(ii); // Store the result of Twalltmp(ii) in a temporary variable
400 if (tempValue < 0)
401 {
402 mon_Ti(ii, 0) = 0.; // If the value is negative, set mon_Ti(ii, 0) to 0
403 }
404 else
405 {
406 mon_Ti(ii, 0) = tempValue; // Otherwise, use the original value
407 }
408 }
409
410 Champ_front_calc& chbis=ref_cast(Champ_front_calc, indicatrice_.valeur());
411 return chbis.initialiser(temps,domaine_Cl_dis().equation().inconnue());
412}
413
415{
416 if (Ti_wall_)
417 Ti_wall_->set_temps_defaut(temps);
418 if (indicatrice_)
419 indicatrice_->set_temps_defaut(temps);
421}
423{
424
425 if (Ti_wall_->valeurs().size() == 1)
426 return Ti_wall_->valeurs()(0, 0);
427 else if (Ti_wall_->valeurs().dimension(1) == 1)
428 return Ti_wall_->valeurs()(i, 0);
429 else
430 Cerr << "Echange_contact_VDF_FT_Disc::Ti_wall_ erreur" << finl;
432 return 0.;
433}
virtual void associer_fr_dis_base(const Frontiere_dis_base &)
Associates a discretized boundary with the field.
virtual DoubleTab & valeurs() override
Returns the array of field values.
virtual void mettre_a_jour(double temps)
DOES NOTHING, to override.
virtual void completer()
class Champ_front_calc Derived class of Champ_front_var representing
void creer(const Nom &, const Nom &, const Motcle &)
Create the Champ_front_calc object representing the trace of an unknown field on a boundary from name...
int initialiser(double, const Champ_Inc_base &) override
Initialization at the beginning of calculation.
void set_distant(int d)
const Milieu_base & milieu() const
Returns the medium associated with the equation carrying the unknown field whose trace is taken.
void fixer_nb_valeurs_temporelles(int nb_cases) override
Overrides Champ_front_base::fixer_nb_valeurs_temporelles.
Domaine_Cl_dis_base & domaine_Cl_dis()
Returns the domain of discretized boundary conditions to which the object belongs.
std::vector< Motcle > app_domains
virtual Frontiere_dis_base & frontiere_dis()
Returns the discretized boundary to which the boundary conditions apply.
Class Conduction: represents the temperature evolution equation.
Definition Conduction.h:41
class Domaine_VF
Definition Domaine_VF.h:44
virtual const DoubleVect & face_surfaces() const
Definition Domaine_VF.h:51
double xv(int num_face, int k) const
Definition Domaine_VF.h:76
int face_voisins(int num_face, int i) const
Returns the neighbouring element of num_face in direction i.
Definition Domaine_VF.h:418
: class Echange_contact_VDF_FT_Disc
virtual double Ti_wall(int num) const
int avancer(double temps) override
Tourne la roue de la CL.
void changer_temps_futur(double temps, int i) override
Change le i-eme temps futur de la CL.
int reculer(double temps) override
Tourne la roue de la CL.
void mettre_a_jour(double) override
Performs a time update of the boundary condition.
void set_temps_defaut(double temps) override
Changes the i-th future time of the BC.
void completer() override
DOES NOTHING must be overridden in derived classes.
int initialiser(double temps) override
Initialization at the beginning of the calculation.
int reculer(double temps) override
Rewinds the boundary condition time wheel.
int initialiser(double temps) override
Initialization at the beginning of the calculation.
void completer() override
DOES NOTHING must be overridden in derived classes.
void changer_temps_futur(double temps, int i) override
Changes the i-th future time of the boundary condition.
void calculer_h_autre_pb(DoubleTab &tab, double invhparoi, int opt)
virtual void calculer_Teta_equiv(DoubleTab &Teta_equiv, const DoubleTab &mon_h, const DoubleTab &autre_h, int is_pb_fluide, double temps)
Fills Teta_eq using T_autre_pb at the time passed as parameter.
int avancer(double temps) override
Advances the boundary condition time wheel.
virtual void calculer_Teta_paroi(DoubleTab &tab_p, const DoubleTab &mon_h, const DoubleTab &autre_h, int is_pb_fluide, double temps)
Fills Teta_p using T_autre_pb at the time passed as parameter.
virtual Champ_front_base & T_autre_pb()
void calculer_h_mon_pb(DoubleTab &, double, int)
void set_temps_defaut(double temps) override
Changes the i-th future time of the BC.
void mettre_a_jour(double temps) override
Performs a time update of the boundary condition.
void fixer_nb_valeurs_temporelles(int nb_cases) override
Called by Conds_lim::completer. Calls cha_front_base::fixer_nb_valeurs_temporelles.
virtual Champ_front_base & T_ext()
Returns the T_ext field of temperature imposed at the boundary.
Class defining operators and methods for all reading operation in an input flow (file,...
Definition Entree.h:42
Schema_Temps_base & schema_temps()
Returns the time scheme associated with the equation.
virtual void fixer_nb_comp(int i)
Sets the number of components of the field.
virtual int nb_comp() const
Definition Field_base.h:56
int_t num_premiere_face() const
Definition Frontiere.h:67
const Nom & le_nom() const override
Returns the name of the Objet_U. Virtual method to override: returns "neant" in this implementation.
Definition Frontiere.h:49
int_t nb_faces() const
Returns the number of faces of the boundary.
Definition Frontiere.h:59
const Frontiere & frontiere() const
Returns the associated geometric boundary.
static Objet_U & objet(const Nom &)
See Interprete_bloc::objet_global(). BM: the Interprete class is not the best place for this.
Milieu_base This class is the base of the (physical) medium hierarchy.
Definition Milieu_base.h:50
virtual const Champ_Don_base & conductivite() const
Returns the conductivity of the medium (const version).
const Equation_base & equation() const
Returns the reference to the equation pointed to by MorEqn::mon_equation.
Definition MorEqn.h:62
class Nom: a character string for naming TRUST objects.
Definition Nom.h:31
const Nom & le_nom() const override
Returns *this.
Definition Nom.cpp:555
virtual Entree & readOn(Entree &)
Reads an Objet_U from an input stream. Virtual method to override.
Definition Objet_U.cpp:289
virtual Sortie & printOn(Sortie &) const
Writes the object to an output stream. Virtual method to override.
Definition Objet_U.cpp:278
@ REQUIRED
Definition Param.h:115
const Triple_Line_Model_FT_Disc & tcl() const
class Probleme_base It is a Probleme_U that is not a coupling.
static double mp_max(double)
Definition Process.cpp:379
static double mp_sum(double)
Computes the sum of x over all processors in the current group.
Definition Process.cpp:145
static void exit(int exit_code=-1)
Exit routine for TRUST within a Kokkos region.
Definition Process.cpp:466
virtual int nb_valeurs_temporelles() const =0
Base class for output streams.
Definition Sortie.h:52
_SIZE_ size_array() const
_SIZE_ dimension(int d) const
Definition TRUSTTab.tpp:133
virtual void detach_vect()
Definition TRUSTVect.h:176
virtual void echange_espace_virtuel(IsExchangeBlocking exchange_type=IsExchangeBlocking::DefaultBlocking, const std::string kernel_name="noname")