TrioCFD 1.9.9_beta
TrioCFD documentation
Loading...
Searching...
No Matches
Partitionneur_Fichier_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 <Partitionneur_Fichier_MED.h>
16#include <EFichier.h>
17#include <Domaine.h>
18#include <medcoupling++.h>
19#include <Param.h>
20#ifdef MEDCOUPLING_
21#include <MEDLoader.hxx>
22#include <MEDCouplingField.hxx>
23#include <MEDCouplingFieldInt32.hxx>
24#pragma GCC diagnostic ignored "-Wreorder"
25#include <MEDFileField.hxx>
26#include <communications.h>
27#include <Champ_Fonc_MED.h>
28#include <EChaine.h>
29
30#endif
31
32// XD Partitionneur_Fichier_MED partitionneur_deriv fichier_med INHERITS_BRACE Partitioning a domain using a MED file
33// XD_CONT containing an integer field providing for each element the processor number on which the element should be
34// XD_CONT located.
35Implemente_instanciable_sans_constructeur(Partitionneur_Fichier_MED,"Partitionneur_Fichier_MED",Partitionneur_base);
36
37Partitionneur_Fichier_MED::Partitionneur_Fichier_MED()
38{
39}
40
42{
43 Cerr << "Partitionneur_MED::printOn invalid\n" << finl;
44 exit();
45 return os;
46}
47
48/*! @brief Reads the partitioner parameters from disk.
49 *
50 * Expected format:
51 * { file FILENAME field FIELDNAME }
52 * FILENAME is the name of a MED file; the FIELDNAME field contains an ArrayOfInt with the processor number.
53 *
54 */
56{
57 param.ajouter("file",&filename_,Param::REQUIRED); // XD_ADD_P chaine
58 // XD_CONT file name of the MED file to load
59 param.ajouter("field",&fieldname_,Param::OPTIONAL); // XD_ADD_P chaine
60 // XD_CONT field name of the integer (or double) field to load
61}
62
64{
65 ref_domaine_ = domaine;
66}
67
69{
70 filename_ = filename;
71}
72
73/*! @brief Reads the content of "filename_" and stores the result in elem_part.
74 *
75 */
76void Partitionneur_Fichier_MED::construire_partition(IntVect& elem_part, int& nb_parts_tot) const
77{
78 if (!ref_domaine_)
79 {
80 Cerr << "Error in Partitionneur_Fichier_MED::construire_partition\n";
81 Cerr << " The domain has not been associated" << finl;
82 exit();
83 }
84 if (filename_ == "")
85 {
86 Cerr << "Error in Partitionneur_Fichier_MED::construire_partition\n";
87 Cerr << " The file name has not been initialized" << finl;
88 exit();
89 }
90 if (fieldname_ == "")
91 {
92 Cerr << "Error in Partitionneur_Fichier_MED::construire_partition\n";
93 Cerr << " The field name has not been initialized" << finl;
94 exit();
95 }
96
97 Cerr << "Reading of splitting file : " << filename_ << finl;
98
99#ifdef MEDCOUPLING_
100 using namespace MEDCoupling;
101
102 MCAuto<MEDCouplingField> ffield = MEDCoupling::ReadField(filename_.getString(), fieldname_.getString());
103 MEDCouplingFieldInt32 * field = dynamic_cast<MEDCouplingFieldInt32 *>((MEDCouplingField *)ffield);
104 if(field)
105 {
106 // Reading an exact partition of the domain given by an integer field
107 DataArrayInt32 *da = field->getArray();
108 const int *field_values = da->begin();
109
110 const mcIdType sz0 = field->getNumberOfTuplesExpected();
111 assert(sz0 < std::numeric_limits<int>::max());
112 const int sz = static_cast<int>(sz0);
113 elem_part.resize(sz);
114 std::copy(field_values, field_values + sz, elem_part.addr());
115 // Sanity check
116 const int nelem = ref_domaine_->nb_elem();
117 if (nelem != sz)
118 {
119 Cerr << "Error in Partitionneur_Fichier_MED::construire_partition" << finl;
120 Cerr << " The file contains an array of " << sz << " values." << finl;
121 Cerr << " The area contains " << nelem << " elements" << finl;
122 exit();
123 }
124 // Checking that the full range is covered
125 MCAuto<DataArrayInt32> das = da->buildUniqueNotSorted();
126 MCAuto<DataArrayInt32> iot(DataArrayInt32::New());
127 mcIdType dnu;
128 const mcIdType max_v = das->getMaxValue(dnu);
129 iot->alloc(max_v + 1, 1);
130 iot->iota();
131 if (!iot->isEqualWithoutConsideringStr(*das))
132 {
133 Cerr << "Error in Partitionneur_Fichier_MED::construire_partition" << finl;
134 Cerr << " The file contains/lacks integer values which do not cover the range [0; n_elem[." << finl;
135 Cerr << " Are some field values missing?" << finl;
136 exit();
137 }
138#else
139 Cerr << "Partitionneur_Fichier_MED requires TRUST compiled with MEDCoupling support!" << finl;
140 exit();
141#endif
142 }
143 else
144 {
145 // Reading a partition of a domain that partially covers the domain, given by a double field:
146 /*
147 Decouper outer_domain {
148 partitionneur metis { nb_parts 3 } zones_name outer_domain
149 ecrire_med outer_domain.med
150 }
151 Decouper inner_domain {
152 partitionneur fichier_med { file outer_domain_0000.med }
153 zones_name inner_domain
154 }
155 */
156 // Read the partition field with Champ_Fonc_MED:
157 Nom cli("");
158 cli+="{ file ";
159 cli+=filename_;
160 cli+=" domain ";
161 cli+= ffield->getMesh()->getName();
162 cli+=" field partition loc elem last_time }";
163 EChaine ech(cli);
164 Champ_Fonc_MED partition_field_outer_domain;
165 ech >> partition_field_outer_domain;
166 // Mapping between local domain and the field domain:
167 int nb_elem = ref_domaine_->nb_elem();
168 DoubleTab xp_elems;
169 ref_domaine_->calculer_centres_gravite(xp_elems);
170 IntVect elems(nb_elem);
171 partition_field_outer_domain.domaine().chercher_elements(xp_elems, elems);
172 DoubleTab double_elem_part(nb_elem);
173 double_elem_part = -1;
174 partition_field_outer_domain.valeur_aux_elems(xp_elems, elems, double_elem_part);
175 if (local_min_vect(double_elem_part)<0)
176 {
177 Cerr << "The domain " << ref_domaine_->le_nom() << " it not fully included into the domain " << ffield->getMesh()->getName() << " ! " << finl;
178 Cerr << "It is mandatory to use the partition field from " << filename_ << finl;
180 }
181 // Convert double to int to fill elem_part:
182 elem_part.resize(nb_elem);
183 for (int i=0; i<nb_elem; i++)
184 elem_part(i)=(int)double_elem_part(i);
185 nb_parts_tot = 1+int(local_max_vect(partition_field_outer_domain.valeurs()));
186 return;
187 }
188}
class Champ_Fonc_MED Load a field from a MED file for a given time.
An input stream whose source is a character string.
Definition EChaine.h:31
class Nom: a character string for naming TRUST objects.
Definition Nom.h:31
virtual void set_param(Param &) const
Definition Objet_U.h:130
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
@ OPTIONAL
Definition Param.h:115
@ REQUIRED
Definition Param.h:115
Partition of a domain from a MED file containing a field giving, for each element,...
void associer_domaine(const Domaine &domaine) override
void initialiser(const char *filename)
void construire_partition(IntVect &elem_part, int &nb_parts_tot) const override
Reads the content of "filename_" and stores the result in elem_part.
static void exit(int exit_code=-1)
Exit routine for TRUST within a Kokkos region.
Definition Process.cpp:466
Base class for output streams.
Definition Sortie.h:52
_TYPE_ * addr()
void resize(_SIZE_, RESIZE_OPTIONS opt=RESIZE_OPTIONS::COPY_INIT)
Definition TRUSTVect.tpp:91