TrioCFD 1.9.9_beta
TrioCFD documentation
Loading...
Searching...
No Matches
Format_Post_Med.cpp
1/****************************************************************************
2* Copyright (c) 2026, 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#include <Format_Post_Med.h>
16#include <Ecrire_MED.h>
17#include <EcrFicPartage.h>
18#include <EFichier.h>
19#include <Param.h>
20#include <med++.h>
21
22Implemente_instanciable_sans_constructeur(Format_Post_Med,"Format_Post_Med",Format_Post_base);
23
24
25/////////////////////////////////////////////////////////////////////////////
26//Parameter: med_basename_
27// Meaning: beginning of the file name
28//Extension med
29
30//Specifics of this format
31//Generation of a format.med.data file usable to rewrite data in another format
32//-Methods completer_post_med(...) and preparer_post_med(...) to generate the files
33//-Method finir_med(...) to concatenate the created files
34///////////////////////////////////////////////////////////////////////////////////////
35
36/*! @brief Default constructor:
37 *
38 */
39
40//Specify in comment what is fixed by default
45
46/*! @brief Resets the object to the state obtained by the default constructor.
47 *
48 */
50{
51 med_basename_ = "??";
52}
53
54/*! @brief erreur => exit
55 *
56 */
58{
59 Cerr << "Format_Post_Med::printOn : error" << finl;
60 exit();
61 return os;
62}
63
64/*! @brief Reads the post-processing parameters in "data set" format. The expected format is:
65 *
66 * {
67 * nom_fichier filename_sans_extension
68 * }
69 *
70 */
72{
74 return is;
75}
76
78{
79 param.ajouter("nom_fichier",&med_basename_,Param::REQUIRED);
80}
81
82/*! @brief Initializes the class with default parameters.
83 */
85{
86 med_basename_= file_basename;
87 return 1;
88}
89
90int Format_Post_Med::initialize(const Nom& file_basename, const int format, const Nom& option_para)
91{
92 med_basename_= file_basename;
93 return 1;
94}
95
96int Format_Post_Med::ecrire_entete(const double temps_courant,const int reprise,const int est_le_premier_post)
97{
98
99 Nom nom_fich(med_basename_);
100 nom_fich +=".";
101 Nom format="med";
102 nom_fich += format;
103 nom_fich += ".index";
104
105 ecrire_entete_med(nom_fich,est_le_premier_post);
106 return 1;
107}
108
109int Format_Post_Med::finir(const int est_le_dernier_post)
110{
111 Nom nom_fic_base(med_basename_);
112 nom_fic_base += ".med";
113 Nom nom_fic=nom_fic_base.nom_me(Process::me());
114 Cerr << "MED file " << nom_fic << " closed. See .index file for more infos." << finl;
115 return 1;
116}
117
118
119int Format_Post_Med::completer_post(const Domaine& dom,const int is_axi,
120 const Nature_du_champ& nature,const int nb_compo,const Noms& noms_compo,
121 const Motcle& loc_post,const Nom& le_nom_champ_post)
122{
123 return 1;
124}
125
126int Format_Post_Med::preparer_post(const Nom& id_du_domaine,const int est_le_premier_post,
127 const int reprise,
128 const double t_init)
129{
130 return 1;
131}
132
133int Format_Post_Med::ecrire_domaine(const Domaine& domaine,const int est_le_premier_post)
134{
135 const OBS_PTR(Domaine_dis_base) domaine_dis_base;
136 return ecrire_domaine_dis(domaine, domaine_dis_base, est_le_premier_post);
137}
138
139void Format_Post_Med::ecrire_domaine_dual(const Domaine& domaine, const int est_le_premier_post)
140{
141 Nom nom_fich(med_basename_);
142 nom_fich +="_dual.";
143 Nom format="med";
144 nom_fich += format;
145
146 bool append = !est_le_premier_post;
147
148 assert(domaine_dis_);
149 ecr_med_.set_file_name_and_dom(nom_fich, domaine, &domaine_dis_.valeur());
150 ecr_med_.ecrire_domaine_dual(append);
151}
152
153/*! @brief voir Format_Post_base::ecrire_domaine
154 */
155int Format_Post_Med::ecrire_domaine_dis(const Domaine& domaine,const OBS_PTR(Domaine_dis_base)& domaine_dis_base,const int est_le_premier_post)
156{
157 domaine_dis_ = domaine_dis_base; // as in base class
158
159 Nom nom_fich(med_basename_);
160 nom_fich +=".";
161 Nom format="med";
162 nom_fich += format;
163 nom_fich += ".index";
164
165 Nom nom_fic_base(med_basename_);
166 nom_fic_base += ".";
167 nom_fic_base += format;
168 Nom nom_fic=nom_fic_base.nom_me(Process::me());
169
170 ecrire_domaine_med(domaine,nom_fic,est_le_premier_post,nom_fich);
171
172 return 1; // ok all is well
173}
174
175/*! @brief Starts writing a new time step.
176 *
177 * Opens the master file in APPEND mode and adds a line
178 * "TEMPS xxxxx" if this time has not yet been written.
179 */
180int Format_Post_Med::ecrire_temps(const double temps)
181{
182 Nom nom_fich(med_basename_);
183 nom_fich +=".";
184 Nom format="med";
185 nom_fich += format;
186 nom_fich += ".index";
187
188 ecrire_temps_med(temps,nom_fich);
189
190 return 1;
191}
192
193/*! @brief voir Format_Post_base::ecrire_champ
194 *
195 */
196int Format_Post_Med::ecrire_champ(const Domaine& domaine,const Noms& unite_,const Noms& noms_compo,
197 int ncomp,double temps_,
198 const Nom& id_champ,
199 const Nom& id_du_domaine,
200 const Nom& localisation,
201 const Nom& nature,
202 const DoubleTab& valeurs)
203{
204 Nom nom_fich_index(med_basename_);
205 nom_fich_index +=".";
206 Nom format="med";
207 nom_fich_index += format;
208 nom_fich_index += ".index";
209
210 Nom nom_fich_ecrit(med_basename_);
211 nom_fich_ecrit += ".";
212 nom_fich_ecrit += format;
213
214 ecrire_champ_med(domaine,unite_,noms_compo,ncomp,temps_,nom_fich_ecrit,id_champ,id_du_domaine,localisation,valeurs,nom_fich_index);
215
216 return 1;
217}
218
219/*! @brief
220 *
221 */
222
224 const Nom& id_du_domaine,
225 const Nom& id_domaine,
226 const Nom& localisation,
227 const Nom& reference,
228 const IntVect& valeurs,
229 const int reference_size)
230{
231
232 return 1;
233}
234
235int Format_Post_Med::ecrire_entete_med(Nom& nom_fich,const int est_le_premier_post)
236{
237
238 if (est_le_premier_post && Process::je_suis_maitre())
239 {
240 SFichier s(nom_fich);
241 s << "TRUST Version " << TRUST_VERSION << finl;
242 s << nom_du_cas() << finl;
243 s << "TRUST" << finl;
244 }
245 return 1;
246}
247
248int Format_Post_Med::finir_med(Nom& nom_fich,int& est_le_dernier_post)
249{
250 ////Nom nom_fichier_base = nom_fich.prefix(".med.index");
251 Nom nom_fichier_base = nom_fich;
252 nom_fichier_base.prefix(".med.index");
253 Nom nom_fichier(nom_fichier_base);
254 Nom format = "med";
255 nom_fichier += ".";
256 nom_fichier += format;
257
258 if (!est_le_dernier_post || !Process::je_suis_maitre()) return 1;
259
260 // we want to concatenate the 3 files
261 SFichier file3(nom_fichier+".data");
262 SFichier file("postmed.data");
263 for (int i=0; i<3; i++)
264 {
265 Nom num(i);
266 Nom fic2(nom_fichier);
267 fic2+=".med";
268 fic2+=num;
269 {
270 EFichier file2(fic2);
271 Nom motlu;
272 file2>>motlu;
273 while (!file2.eof())
274 {
275 file<<motlu<<" "<<finl;
276 if (motlu!="#")
277 file3<<motlu<<" "<<finl;
278 file2>>motlu;
279 }
280 }
281 }
282
283 SFichier s;
284 s.ouvrir(nom_fich,ios::app);
285 s << "FIN" << finl;
286
287 return 1;
288}
289
290int Format_Post_Med::completer_post_med(const Nom& nom_fich2,const Nom& nom1,const Nom& nom2)
291{
292 if (je_suis_maitre())
293 {
294 SFichier file;
295 file.ouvrir(nom_fich2,ios::app);
296 file <<nom1<<" "<<nom2<<finl;
297 }
298 return 1;
299}
300
301int Format_Post_Med::preparer_post_med(const Nom& nom_fich1,const Nom& nom_fich2,const Nom& nom_fich3,
302 const Nom& id_du_domaine,const int est_le_premier_post)
303{
304 Nom nom_fich(nom_fich1);
305 nom_fich.prefix(".med0");
306
307 if (!je_suis_maitre()) return 1;
308
309 if (est_le_premier_post)
310 {
311 SFichier file(nom_fich1);
312 file<<"{ Dimension "<<dimension<<finl<<"# export Domaine "<<id_du_domaine<<finl;
313 }
314 else
315 {
316 SFichier file(nom_fich1,ios::app);
317 file<<" export Domaine "<<id_du_domaine<<finl;
318 }
319
320 SFichier file;
321 if (est_le_premier_post)
322 {
323 file.ouvrir(nom_fich2);
324 file<<"# \n Pbc_MED pbmed\n Lire pbmed { "<<finl;
325 }
326 else
327 {
328 file.ouvrir(nom_fich2,ios::app);
329 file<<"} } } , "<<finl;
330 }
331 file<<nom_fich<<" "<<id_du_domaine<<" { Postraitement { Champs dt_post 1e-9 {"<<finl;
332
333 if (est_le_premier_post)
334 {
335 SFichier file2(nom_fich3);
336 file2<<"} } } } }"<<finl;
337 }
338
339 return 1;
340}
341
342int Format_Post_Med::ecrire_domaine_med(const Domaine& domaine,const Nom& nom_fic,const int est_le_premier_post,Nom& nom_fich)
343{
344 int dim = domaine.les_sommets().dimension(1);
345 bool append = !est_le_premier_post;
346 if (je_suis_maitre())
347 {
348 SFichier s;
349 s.ouvrir(nom_fich, ios::app);
350 s << "format MED: " << ecr_med_.version() << finl;
351 s << "dimension: " << dim << finl;
352 s << "domaine: " << domaine.le_nom() << finl;
353 s << "nb_proc: " << Process::nproc() << finl;
354 Cerr << "Opening MED file " << nom_fic << " with " << ecr_med_.version() << " format. ";
355 Cerr << finl;
356 }
357 ecr_med_.set_file_name_and_dom(nom_fic, domaine, domaine_dis_ ? &domaine_dis_.valeur() : nullptr);
358 ecr_med_.ecrire_domaine_dis(append);
359 return 1;
360
361}
362
363int Format_Post_Med::ecrire_temps_med(const double temps,Nom& nom_fich)
364{
365 if (je_suis_maitre())
366 {
367 SFichier s;
368 s.ouvrir(nom_fich,ios::app);
369 s << "TEMPS " << temps << finl;
370 }
371 return 1;
372}
373
374int Format_Post_Med::ecrire_champ_med(const Domaine& dom,const Noms& unite_, const Noms& noms_compo,
375 int ncomp, double temps_,const Nom& nom_pdb,
376 const Nom& id_du_champ,
377 const Nom& id_du_domaine,
378 const Nom& loc_post,
379 const DoubleTab& valeurs,Nom& nom_fich)
380{
381 Nom fic = nom_pdb.nom_me(me());
382 ecr_med_.set_file_name_and_dom(fic, dom, domaine_dis_ ? &domaine_dis_.valeur() : nullptr);
383
384 Nom nom_post(id_du_champ);
385 Noms noms_compo_courts(noms_compo);
386 if (ncomp != -1)
387 {
388 nom_post = noms_compo[ncomp];
389 }
390 nom_post.prefix(dom.le_nom());
391 Nom nom_dom="";
392 for (int i = 0; i < noms_compo.size(); ++i)
393 noms_compo_courts[i] = Motcle(noms_compo_courts[i]).getPrefix(dom.le_nom());
394 if (loc_post == "SOM")
395 {
396 nom_post.prefix("_som_");
397 nom_post.prefix("_SOM_");
398 nom_dom = dom.le_nom();
399 for (int i = 0; i < noms_compo.size(); ++i)
400 noms_compo_courts[i] = Motcle(noms_compo_courts[i]).getPrefix("_SOM_");
401 }
402 else if (loc_post == "ELEM")
403 {
404 nom_post.prefix("_ELEM_");
405 nom_post.prefix("_elem_");
406 nom_dom = dom.le_nom();
407 for (int i = 0; i < noms_compo.size(); ++i)
408 noms_compo_courts[i] = Motcle(noms_compo_courts[i]).getPrefix("_ELEM_");
409 }
410 else if (loc_post == "FACES")
411 {
412#ifdef MEDCOUPLING_
413 nom_post.prefix("_FACES_");
414 nom_post.prefix("_faces_");
415 nom_dom = dom.le_nom();
416 for (int i = 0; i < noms_compo.size(); ++i)
417 noms_compo_courts[i] = Motcle(noms_compo_courts[i]).getPrefix("_FACES_");
418#else
419 Cerr << "Post-processing in MED format on faces needs MEDCoupling" << finl;
420#endif
421 }
422 if (je_suis_maitre())
423 {
424 //Opening the file
425 SFichier os;
426 os.ouvrir(nom_fich, ios::app);
427 os << "champ: " << nom_post << " " << nom_dom << " " << loc_post << finl;
428 }
429
430 Nom type_elem = dom.type_elem()->que_suis_je();
431
432 // modify component names
433 for (int i = 0; i < noms_compo.size(); ++i)
434 noms_compo_courts[i] = Motcle(noms_compo_courts[i]).getSuffix(nom_post);
435
436 if (loc_post == "SOM")
437 ecr_med_.ecrire_champ("CHAMPPOINT", id_du_champ, valeurs, unite_, noms_compo_courts, type_elem, temps_);
438 else if (loc_post == "ELEM")
439 ecr_med_.ecrire_champ("CHAMPMAILLE", id_du_champ, valeurs, unite_, noms_compo_courts, type_elem, temps_);
440 else if (loc_post == "FACES")
441 ecr_med_.ecrire_champ("CHAMPFACES", id_du_champ, valeurs, unite_, noms_compo_courts, type_elem, temps_);
442 else
443 {
444 Cerr << "We do not know to postprocess " << id_du_champ
445 << " with the keyword " << loc_post << finl;
446 return -1;
447 }
448 return 1;
449}
const Nom & le_nom() const override
Returns the name of the Objet_U. Virtual method to override: returns "neant" in this implementation.
class Domaine_dis_base This class is the base of the hierarchy of discretized domains.
File for reading. This class is to the C++ ifstream class what the Entree class is to the.
Definition EFichier.h:29
Class defining operators and methods for all reading operation in an input flow (file,...
Definition Entree.h:42
: Post-processing class for Eulerian fields in MED format.
Format_Post_Med()
Default constructor:
void reset() override
Resets the object to the state obtained by the default constructor.
int ecrire_domaine_dis(const Domaine &domaine, const OBS_PTR(Domaine_dis_base)&domaine_dis_base, const int est_le_premier_post) override
voir Format_Post_base::ecrire_domaine
Ecrire_MED ecr_med_
int completer_post(const Domaine &dom, const int axi, const Nature_du_champ &nature, const int nb_compo, const Noms &noms_compo, const Motcle &loc_post, const Nom &le_nom_champ_post) override
Nom med_basename_
int ecrire_domaine(const Domaine &domaine, const int est_le_premier_post) override
Writing a mesh.
virtual int preparer_post_med(const Nom &nom_fich1, const Nom &nom_fich2, const Nom &nom_fich3, const Nom &id_du_domaine, const int est_le_premier_post)
virtual int finir_med(Nom &nom_fic, int &est_le_dernier_post)
virtual int completer_post_med(const Nom &nom_fich2, const Nom &nom1, const Nom &nom2)
int ecrire_item_int(const Nom &id_item, const Nom &id_du_domaine, const Nom &id_domaine, const Nom &localisation, const Nom &reference, const IntVect &data, const int reference_size) override
Writing an integer array to the post-processing file.
virtual int ecrire_champ_med(const Domaine &domaine, const Noms &unite_, const Noms &noms_compo, int ncomp, double temps_, const Nom &nom_pdb, const Nom &id_du_champ, const Nom &id_du_domaine, const Nom &localisation, const DoubleTab &data, Nom &nom_fich)
int initialize_by_default(const Nom &file_basename) override
Initializes the class with default parameters.
virtual int ecrire_temps_med(const double temps, Nom &nom_fich)
virtual int ecrire_entete_med(Nom &nom_fic, const int est_le_premier_post)
void ecrire_domaine_dual(const Domaine &domaine, const int est_le_premier_post) override
int ecrire_champ(const Domaine &domaine, const Noms &unite_, const Noms &noms_compo, int ncomp, double temps_, const Nom &id_du_champ, const Nom &id_du_domaine, const Nom &localisation, const Nom &nature, const DoubleTab &data) override
voir Format_Post_base::ecrire_champ
void set_param(Param &param) const override
int ecrire_temps(const double temps) override
Starts writing a new time step.
int preparer_post(const Nom &id_du_domaine, const int est_le_premier_post, const int reprise, const double t_init) override
int ecrire_entete(const double temps_courant, const int reprise, const int est_le_premier_post) override
int initialize(const Nom &file_basename, const int format, const Nom &option_para) override
int finir(const int est_le_dernier_post) override
virtual int ecrire_domaine_med(const Domaine &domaine, const Nom &nom_fic, const int est_le_premier_post, Nom &nom_fich)
Base class for post-processing output formats for fields (lata, med, cgns, lml, single_lata).
OBS_PTR(Domaine_dis_base) domaine_dis_
Reference to the discretized domain - used for face fields.
A character string (Nom) in uppercase.
Definition Motcle.h:26
class Nom: a character string for naming TRUST objects.
Definition Nom.h:31
const Nom getPrefix(const char *const) const
Definition Nom.cpp:335
Nom nom_me(int, const char *prefix=0, int without_padding=0) const
Inserts _prefix000n (n=me() or nproc()) into a file name (e.g. toto.titi) to produce toto_prefix000n....
Definition Nom.cpp:380
const Nom getSuffix(const char *const) const
Definition Nom.cpp:276
Nom & prefix(const char *const)
Definition Nom.cpp:324
An array of character strings (VECT(Nom)).
Definition Noms.h:26
static int dimension
Definition Objet_U.h:94
const Nom & que_suis_je() const
Returns the string identifying the class.
Definition Objet_U.cpp:104
virtual Entree & readOn(Entree &)
Reads an Objet_U from an input stream. Virtual method to override.
Definition Objet_U.cpp:289
static const Nom & nom_du_cas()
Returns a constant reference to the case name. This method is static.
Definition Objet_U.cpp:145
virtual const Nom & le_nom() const
Returns the name of the Objet_U. Virtual method to override: returns "neant" in this implementation.
Definition Objet_U.cpp:317
virtual Sortie & printOn(Sortie &) const
Writes the object to an output stream. Virtual method to override.
Definition Objet_U.cpp:278
Helper class to factorize the readOn method of Objet_U classes.
Definition Param.h:112
void ajouter(const char *keyword, const int *value, Param::Nature nat=Param::OPTIONAL)
Register an integer parameter.
Definition Param.cpp:364
@ REQUIRED
Definition Param.h:115
static int nproc()
Returns the number of processors in the current group. See Comm_Group::nproc() and PE_Groups::current...
Definition Process.cpp:102
static int me()
Returns the rank of the local processor in the current communication group. See Comm_Group::rank() an...
Definition Process.cpp:122
static void exit(int exit_code=-1)
Exit routine for TRUST within a Kokkos region.
Definition Process.cpp:466
static int je_suis_maitre()
Returns 1 if on the master processor of the current group (i.e. me() == 0), 0 otherwise.
Definition Process.cpp:82
SFichier is to the C++ ofstream class what Sortie is to the C++ ostream class.
Definition SFichier.h:29
virtual int ouvrir(const char *name, IOS_OPEN_MODE mode=ios::out)
Base class for output streams.
Definition Sortie.h:52