1 // Copyright (C) 2007-2020 CEA/DEN, EDF R&D
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License, or (at your option) any later version.
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 // Lesser General Public License for more details.
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
20 #include "MEDPARTITIONER_MeshCollection.hxx"
21 #include "MEDPARTITIONER_Topology.hxx"
22 #include "MEDPARTITIONER_Graph.hxx"
23 #include "MEDPARTITIONER_ParaDomainSelector.hxx"
24 #include "MEDPARTITIONER_ParallelTopology.hxx"
25 #include "MEDPARTITIONER_ConnectZone.hxx"
26 #include "MEDPARTITIONER_Utils.hxx"
28 #include "MEDCouplingSkyLineArray.hxx"
29 #include "MEDCouplingUMesh.hxx"
30 #include "InterpKernelHashMap.hxx"
31 #include "MCIdType.hxx"
42 using namespace MEDPARTITIONER;
44 ParallelTopology::ParallelTopology():_nb_domain(0),_mesh_dimension(0)
48 //constructing topology according to mesh collection without global numerotation (use setGlobalNumerotation later)
49 ParallelTopology::ParallelTopology(const std::vector<MEDCoupling::MEDCouplingUMesh*>& meshes)
51 _nb_domain=(int)meshes.size();
52 _nb_cells.resize(_nb_domain);
53 _nb_nodes.resize(_nb_domain);
54 // _nb_faces.resize(_nb_domain);
56 if (MyGlobals::_Is0verbose>100)
57 std::cout << "new ParallelTopology\n";
58 _loc_to_glob.resize(0); //precaution, need gatherNbOf() setGlobalNumerotation()
59 _node_loc_to_glob.resize(0); //precaution, need gatherNbOf() setGlobalNumerotation()
60 //_face_loc_to_glob.resize(_nb_domain);
62 bool parallel_mode = false;
63 for (int idomain=0; !parallel_mode && idomain<_nb_domain; idomain++)
64 parallel_mode = (!meshes[idomain]);
66 if (MyGlobals::_Is0verbose>20 && !parallel_mode)
67 std::cout << "WARNING : ParallelTopology constructor without parallel_mode" << std::endl;
68 for (int idomain=0; idomain<_nb_domain; idomain++)
70 if ( !meshes[idomain] ) continue;
71 if (_mesh_dimension==-1)
73 _mesh_dimension = meshes[idomain]->getMeshDimension();
77 if (_mesh_dimension!=meshes[idomain]->getMeshDimension())
78 throw INTERP_KERNEL::Exception("meshes dimensions incompatible");
80 _nb_cells[idomain]=meshes[idomain]->getNumberOfCells();
81 _nb_nodes[idomain]=meshes[idomain]->getNumberOfNodes();
82 //note: in parallel mode _nb_cells and _nb_nodes are not complete now, needs gatherNbOf()
86 //constructing _loc_to_glob etc by default, needs gatherNbOf() done
87 void ParallelTopology::setGlobalNumerotationDefault(ParaDomainSelector* domainSelector)
89 if (MyGlobals::_Is0verbose>100)
90 std::cout<< "setGlobalNumerotationDefault on " << _nb_domain << " domains\n";
91 if (_loc_to_glob.size()!=0) throw INTERP_KERNEL::Exception("a global numerotation is done yet");
92 _loc_to_glob.resize(_nb_domain);
93 _node_loc_to_glob.resize(_nb_domain);
95 //warning because _nb_cells[idomain] is 0 if not my domain(s)
96 //we set loc_to_glob etc.. only for my domain(s)
97 if (MyGlobals::_Is0verbose>500)
98 std::cout << "(c)idomain|ilocalCell|iglobalCell" << std::endl;
99 for (int idomain=0; idomain<_nb_domain; idomain++)
101 _loc_to_glob[idomain].resize(_nb_cells[idomain]);
102 mcIdType domainCellShift=domainSelector->getDomainCellShift(idomain);
103 for (mcIdType i=0; i<_nb_cells[idomain]; i++)
105 mcIdType global=domainCellShift+i ;
106 _glob_to_loc.insert(std::make_pair(global,std::make_pair(idomain,i)));
107 _loc_to_glob[idomain][i]=global;
108 if (MyGlobals::_Verbose>500)
109 std::cout << "c" << idomain << "|" << i << "|" << global << " ";
113 if (MyGlobals::_Verbose>500 && MyGlobals::_World_Size>1) MPI_Barrier(MPI_COMM_WORLD); //synchronize verbose trace
115 if (MyGlobals::_Is0verbose>500) std::cout << std::endl;
117 if (MyGlobals::_Is0verbose>500) std::cout << "(n)idomain|ilocalNode|iglobalNode" << std::endl;
118 for (int idomain=0; idomain<_nb_domain; idomain++)
120 _node_loc_to_glob[idomain].resize(_nb_nodes[idomain]);
121 mcIdType domainNodeShift=domainSelector->getDomainNodeShift(idomain);
122 for (mcIdType i=0; i<_nb_nodes[idomain]; i++)
124 mcIdType global=domainNodeShift+i ;
125 _node_glob_to_loc.insert(std::make_pair(global,std::make_pair(idomain,i)));
126 _node_loc_to_glob[idomain][i]=global;
127 if (MyGlobals::_Verbose>500)
128 std::cout << "n" << idomain << "|" << i << "|" << global << " ";
132 if (MyGlobals::_Verbose>500 && MyGlobals::_World_Size>1) MPI_Barrier(MPI_COMM_WORLD); //synchronize verbose trace
134 if (MyGlobals::_Is0verbose>500) std::cout << std::endl;
136 _nb_total_cells=domainSelector->getNbTotalCells();
137 _nb_total_nodes=domainSelector->getNbTotalNodes();
138 _nb_total_faces=domainSelector->getNbTotalFaces();
139 if (MyGlobals::_Is0verbose>200)
140 std::cout << "globalNumerotation default done meshDimension " << _mesh_dimension << " nbTotalCells " << _nb_total_cells << " nbTotalNodes " << _nb_total_nodes << std::endl;
143 //constructing topology according to mesh collection
144 ParallelTopology::ParallelTopology(const std::vector<MEDCoupling::MEDCouplingUMesh*>& meshes,
145 const std::vector<MEDPARTITIONER::ConnectZone*>& cz,
146 std::vector<mcIdType*>& cellglobal,
147 std::vector<mcIdType*>& nodeglobal,
148 std::vector<mcIdType*>& faceglobal)
150 _nb_domain=(int)meshes.size();
151 mcIdType index_global=0;
152 mcIdType index_node_global=0;
153 mcIdType index_face_global=0;
155 _nb_cells.resize(_nb_domain);
156 _nb_nodes.resize(_nb_domain);
157 // _nb_faces.resize(_nb_domain);
159 _loc_to_glob.resize(_nb_domain);
160 _node_loc_to_glob.resize(_nb_domain);
161 // _face_loc_to_glob.resize(_nb_domain);
163 bool parallel_mode = false;
164 for (int idomain=0; !parallel_mode && idomain<_nb_domain; idomain++)
165 parallel_mode = (!meshes[idomain]);
167 for (int idomain=0; idomain<_nb_domain; idomain++)
169 if ( !meshes[idomain] ) continue;
170 _mesh_dimension = meshes[idomain]->getMeshDimension();
173 _nb_cells[idomain]=meshes[idomain]->getNumberOfCells();
174 // cout << "Nb cells (domain "<<idomain<<") = "<<_nb_cells[idomain];
175 _loc_to_glob[idomain].resize(_nb_cells[idomain]);
177 if (cellglobal[idomain]==0 || parallel_mode)
179 //int cellDomainShift=_cell_shift_by_domain[idomain];
180 //creating global numbering from scratch
181 for (mcIdType i=0; i<_nb_cells[idomain]; i++)
183 mcIdType global=i ;//cellDomainShift+i;
184 _glob_to_loc.insert(std::make_pair(global,std::make_pair(idomain,i)));
185 _loc_to_glob[idomain][i]=global;
189 //using global numbering coming from a previous numbering
192 for (mcIdType i=0; i<_nb_cells[idomain]; i++)
194 mcIdType global=cellglobal[idomain][i];
195 _glob_to_loc.insert(std::make_pair(global,std::make_pair(idomain,i)));
196 //_loc_to_glob[make_pair(idomain,i+1)]=global;
197 _loc_to_glob[idomain][i]=global;
205 _nb_total_cells=index_global;
206 _nb_cells[0]=index_global;
207 _node_loc_to_glob[idomain].resize(meshes[idomain]->getNumberOfNodes());
208 for (mcIdType i=0; i<meshes[idomain]->getNumberOfNodes(); i++)
210 _node_glob_to_loc.insert(std::make_pair(i,std::make_pair(0,i)));
211 _node_loc_to_glob[0][i]=i;
213 _nb_total_nodes=meshes[idomain]->getNumberOfNodes();
214 _nb_nodes[0]=_nb_total_nodes;
219 _nb_nodes[idomain]=meshes[idomain]->getNumberOfNodes();
220 INTERP_KERNEL::HashMap <mcIdType,std::pair<int,mcIdType> > local2distant;
221 _node_loc_to_glob[idomain].resize(_nb_nodes[idomain]);
222 for (std::size_t icz=0; icz<cz.size(); icz++)
224 if (cz[icz]->getLocalDomainNumber() == idomain &&
225 cz[icz]->getLocalDomainNumber()>cz[icz]->getDistantDomainNumber())
227 mcIdType nb_node= cz[icz]->getNodeNumber();
228 const mcIdType* node_corresp=cz[icz]->getNodeCorrespValue();
229 int distant_ip = cz[icz]->getDistantDomainNumber();
230 for (mcIdType i=0; i< nb_node; i++)
232 mcIdType local= node_corresp[i*2];
233 mcIdType distant = node_corresp[i*2+1];
234 local2distant.insert(std::make_pair(local, std::make_pair(distant_ip,distant)));
238 // setting mappings for all nodes
239 if (nodeglobal[idomain]==0)
241 for (mcIdType inode=0; inode<_nb_nodes[idomain]; inode++)
243 if (local2distant.find(inode)==local2distant.end())
246 _node_glob_to_loc.insert(std::make_pair(index_node_global,std::make_pair(idomain,inode)));
247 //_node_loc_to_glob[make_pair(idomain,inode+1)]=index_node_global;
248 _node_loc_to_glob[idomain][inode]=index_node_global;
252 int ip = (local2distant.find(inode)->second).first;
253 mcIdType distant = (local2distant.find(inode)->second).second;
254 mcIdType global_number=_loc_to_glob[ip][distant];
255 _node_glob_to_loc.insert(std::make_pair(global_number,std::make_pair(idomain,inode)));
256 _node_loc_to_glob[idomain][inode]=global_number;
260 //using former node numbering
263 for (mcIdType inode=0; inode<_nb_nodes[idomain]; inode++)
265 mcIdType global_number=nodeglobal[idomain][inode];
266 _node_glob_to_loc.insert(std::make_pair(global_number,std::make_pair(idomain,inode)));
267 _node_loc_to_glob[idomain][inode]=global_number;
272 _nb_total_cells=index_global;
273 _nb_total_nodes=index_node_global;
274 _nb_total_faces=index_face_global;
278 //constructing ParallelTopology from an old topology and a graph
279 ParallelTopology::ParallelTopology(Graph* graph, Topology* oldTopology, int nb_domain, int mesh_dimension)
282 _nb_domain=nb_domain;
283 _mesh_dimension=mesh_dimension;
285 if (MyGlobals::_Verbose>200)
286 std::cout << "proc " << MyGlobals::_Rank << " : new topology oldNbDomain " <<
287 oldTopology->nbDomain() << " newNbDomain " << _nb_domain << std::endl;
288 _nb_cells.resize(_nb_domain,0);
289 _nb_nodes.resize(_nb_domain,0);
290 _nb_faces.resize(_nb_domain,0);
292 _loc_to_glob.resize(_nb_domain);
293 _node_loc_to_glob.resize(_nb_domain);
294 _face_loc_to_glob.resize(_nb_domain);
296 const mcIdType* part=graph->getPart(); //all cells for this proc (may be more domains)
297 _nb_total_cells=graph->nbVertices(); //all cells for this proc (may be more domains)
298 if (MyGlobals::_Verbose>300)
299 std::cout << "proc " << MyGlobals::_Rank << " : topology from partition, nbTotalCells " << _nb_total_cells << std::endl;
301 int icellProc=0; //all cells of my domains are concatenated in part
302 for (int iold=0; iold<oldTopology->nbDomain(); iold++)
304 mcIdType ioldNbCell=oldTopology->getCellNumber(iold);
305 //std::cout<<"proc "<<MyGlobals::_Rank<<" : cell number old domain "<<iold<<" : "<<ioldNbCell<<std::endl;
306 //if not my old domains getCellNumber is 0
307 std::vector<mcIdType> globalids(ioldNbCell);
308 oldTopology->getCellList(iold, &globalids[0]); //unique global numerotation
309 for (mcIdType icell=0; icell<ioldNbCell; icell++)
311 int idomain=FromIdType<int>(part[icellProc]);
312 _nb_cells[idomain]++;
314 mcIdType iGlobalCell=globalids[icell];
315 _loc_to_glob[idomain].push_back(iGlobalCell);
316 _glob_to_loc.insert(std::make_pair(iGlobalCell, std::make_pair(idomain, _nb_cells[idomain])));
320 if (MyGlobals::_Verbose>300)
321 for (int idomain=0; idomain<_nb_domain; idomain++)
322 std::cout << "proc " << MyGlobals::_Rank << " : nbCells in new domain " << idomain << " : " << _nb_cells[idomain] << std::endl;
326 if ( MyGlobals::_Create_Joints && nb_domain > 1 )
328 std::vector< std::vector< std::vector< mcIdType > > > cellCorresp( nb_domain );
329 for ( int idomain = 0; idomain < nb_domain; ++idomain )
331 cellCorresp[ idomain ].resize( nb_domain );
333 const MEDCoupling::MEDCouplingSkyLineArray* skylinegraph = graph->getGraph();
334 const mcIdType* index = skylinegraph->getIndex();
335 const mcIdType* value = skylinegraph->getValues();
336 const mcIdType nbCells = skylinegraph->getNumberOf();
338 for ( mcIdType iGlob = 0; iGlob < nbCells; ++iGlob )
340 int iGlobDom = FromIdType<int>(part[ iGlob ]);
341 for ( mcIdType i = index[ iGlob ]; i < index[ iGlob+1 ]; i++ )
343 mcIdType iGlobNear = value[ i ];
344 if ( iGlob > iGlobNear )
345 continue; // treat ( iGlob, iGlobNear ) pair once
346 int iGlobNearDom = FromIdType<int>(part[ iGlobNear ]);
347 if ( iGlobDom != iGlobNearDom )
349 mcIdType iLoc = convertGlobalCell( iGlob ).second - 1; // to MEDCoupling fmt
350 mcIdType iLocNear = convertGlobalCell( iGlobNear ).second - 1;
351 cellCorresp[ iGlobDom ][ iGlobNearDom ].push_back( iLoc );
352 cellCorresp[ iGlobDom ][ iGlobNearDom ].push_back( iLocNear );
353 cellCorresp[ iGlobNearDom ][ iGlobDom ].push_back( iLocNear );
354 cellCorresp[ iGlobNearDom ][ iGlobDom ].push_back( iLoc );
358 for ( int idomain = 0; idomain < nb_domain; ++idomain )
360 for ( int idomainNear = 0; idomainNear < nb_domain; ++idomainNear )
362 std::vector< mcIdType > & corresp = cellCorresp[ idomain ][ idomainNear ];
363 if ( corresp.empty() )
365 MEDPARTITIONER::ConnectZone* cz = new MEDPARTITIONER::ConnectZone();
366 cz->setName( "Connect Zone defined by MEDPARTITIONER" );
367 cz->setDistantDomainNumber( idomainNear );
368 cz->setLocalDomainNumber ( idomain );
369 cz->setEntityCorresp( 0,0, &corresp[0], ToIdType( corresp.size()/2 ));
370 _connect_zones.push_back( cz );
376 ParallelTopology::~ParallelTopology()
378 for ( size_t i = 0; i < _connect_zones.size(); ++i )
380 delete _connect_zones[i];
381 _connect_zones[i] = 0;
383 _connect_zones.clear();
386 /*!Converts a list of global node numbers
387 * to a distributed array with local cell numbers.
389 * If a node in the list is represented on several domains,
390 * only the first value is returned
392 void ParallelTopology::convertGlobalNodeList(const mcIdType* node_list, mcIdType nbnode, mcIdType* local, int* ip)
394 if (_node_glob_to_loc.empty())
395 throw INTERP_KERNEL::Exception("Node mapping has not yet been built");
396 for (mcIdType i=0; i< nbnode; i++)
398 std::pair<int,mcIdType> local_node = _node_glob_to_loc.find(node_list[i])->second;
399 ip[i]=local_node.first;
400 local[i]=local_node.second;
404 /*!Converts a list of global node numbers on domain ip
405 * to a distributed array with local cell numbers.
407 * If a node in the list is represented on several domains,
408 * only the value with domain ip is returned
411 void ParallelTopology::convertGlobalNodeList(const mcIdType* node_list, mcIdType nbnode, mcIdType* local, int ip)
413 if (_node_glob_to_loc.empty())
414 throw INTERP_KERNEL::Exception("Node mapping has not yet been built");
416 for (mcIdType i=0; i< nbnode; i++)
418 typedef INTERP_KERNEL::HashMultiMap<mcIdType,std::pair<int,mcIdType> >::iterator mmiter;
419 std::pair<mmiter,mmiter> range=_node_glob_to_loc.equal_range(node_list[i]);
420 for (mmiter it=range.first; it !=range.second; it++)
422 int ipfound=(it->second).first;
424 local[i]=(it->second).second;
429 /*!Converts a list of global node numbers
430 * to a distributed array with local cell numbers.
432 * If a node in the list is represented on several domains,
433 * all the values are put in the array
435 void ParallelTopology::convertGlobalNodeListWithTwins(const mcIdType* node_list, mcIdType nbnode, mcIdType*& local, int*& ip,mcIdType*& full_array, mcIdType& size)
437 if (_node_glob_to_loc.empty())
438 throw INTERP_KERNEL::Exception("Node mapping has not yet been built");
441 for (mcIdType i=0; i< nbnode; i++)
443 mcIdType count= ToIdType( _node_glob_to_loc.count(node_list[i]));
448 local=new mcIdType[size];
449 full_array=new mcIdType[size];
450 for (mcIdType i=0; i< nbnode; i++)
452 typedef INTERP_KERNEL::HashMultiMap<mcIdType,std::pair<int,mcIdType> >::iterator mmiter;
453 std::pair<mmiter,mmiter> range=_node_glob_to_loc.equal_range(node_list[i]);
454 for (mmiter it=range.first; it !=range.second; it++)
456 ip[index]=(it->second).first;
457 local[index]=(it->second).second;
458 full_array [index]=node_list[i];
465 /*!Converts a list of global face numbers
466 * to a distributed array with local face numbers.
468 * If a face in the list is represented on several domains,
469 * all the values are put in the array
471 void ParallelTopology::convertGlobalFaceListWithTwins(const mcIdType* face_list, mcIdType nbface, mcIdType*& local, int*& ip, mcIdType*& full_array,mcIdType& size)
474 for (mcIdType i=0; i< nbface; i++)
476 //int count = _face_glob_to_loc.count(face_list[i]);
477 //if (count >1) MESSAGE_MED("face en doublon "<<face_list[i]);
478 size+= ToIdType(_face_glob_to_loc.count(face_list[i]));
482 local=new mcIdType[size];
483 full_array=new mcIdType[size];
484 for (mcIdType i=0; i< nbface; i++)
486 typedef INTERP_KERNEL::HashMultiMap<mcIdType,std::pair<int,mcIdType> >::iterator mmiter;
487 std::pair<mmiter,mmiter> range=_face_glob_to_loc.equal_range(face_list[i]);
488 for (mmiter it=range.first; it !=range.second; it++)
490 ip[index]=(it->second).first;
491 local[index]=(it->second).second;
492 full_array[index]=face_list[i];
499 //!converts a list of global cell numbers
500 //!to a distributed array with local cell numbers
501 void ParallelTopology::convertGlobalCellList(const mcIdType* cell_list, mcIdType nbcell, mcIdType* local, int* ip)
503 for (mcIdType i=0; i<nbcell; i++)
505 INTERP_KERNEL::HashMap<mcIdType, std::pair<int,mcIdType> >::const_iterator iter = _glob_to_loc.find(cell_list[i]);
506 if (iter == _glob_to_loc.end())
508 std::cerr << "proc " << MyGlobals::_Rank << " : KO cell_list[" << i << "] : " << cell_list[i] << std::endl;
509 throw INTERP_KERNEL::Exception("ParallelTopology::convertGlobalCellList : Cell not found");
513 ip[i]=(iter->second).first; //no domain
514 local[i]=(iter->second).second; //no local cell
519 /*!Converts a list of global face numbers
520 * to a distributed array with local face numbers
522 void ParallelTopology::convertGlobalFaceList(const mcIdType* face_list, mcIdType nbface, mcIdType* local, int* ip)
524 for (mcIdType i=0; i< nbface; i++)
526 INTERP_KERNEL::HashMap<mcIdType, std::pair<int,mcIdType> >::const_iterator iter = _face_glob_to_loc.find(face_list[i]);
527 if (iter == _face_glob_to_loc.end())
529 throw INTERP_KERNEL::Exception("ParallelTopology::convertGlobalFaceList : Face not found");
531 ip[i]=(iter->second).first;
532 local[i]=(iter->second).second;
536 /*!Converts a list of global node numbers on domain ip
537 * to a distributed array with local cell numbers.
539 * If a node in the list is represented on several domains,
540 * only the value with domain ip is returned
543 void ParallelTopology::convertGlobalFaceList(const mcIdType* face_list, mcIdType nbface, mcIdType* local, int ip)
545 for (mcIdType i=0; i< nbface; i++)
547 typedef INTERP_KERNEL::HashMultiMap<mcIdType,std::pair<int,mcIdType> >::iterator mmiter;
548 std::pair<mmiter,mmiter> range=_face_glob_to_loc.equal_range(face_list[i]);
549 for (mmiter it=range.first; it !=range.second; it++)
551 int ipfound=(it->second).first;
553 local[i]=(it->second).second;
559 //replacing a table of global numbering with a table with local numberings
560 // type_connectivity contains global connectivity for each type in input
561 // type_connectivity contains local connectivity for each type in output
562 void ParallelTopology::convertToLocal2ndVersion(mcIdType* nodes, mcIdType nbnodes, int idomain)
564 for (mcIdType inode=0; inode<nbnodes; inode++)
566 // cout <<" inode :"<<inode<< " global = "<<type_connectivity[type][inode];
567 mcIdType global = nodes[inode];
568 typedef INTERP_KERNEL::HashMultiMap<mcIdType,std::pair<int,mcIdType> >::iterator mmiter;
569 std::pair<mmiter,mmiter> range=_node_glob_to_loc.equal_range(global);
570 for (mmiter it=range.first; it !=range.second; it++)
572 if ((it->second).first==idomain)
573 nodes[inode]=(it->second).second;
579 * \brief Return max global face number
581 mcIdType ParallelTopology::getMaxGlobalFace() const
584 TGlob2LocsMap::const_iterator g_l_l = _face_glob_to_loc.begin();
585 for ( ; g_l_l != _face_glob_to_loc.end(); ++g_l_l )
586 if ( g_l_l->first > max )
591 mcIdType ParallelTopology::getNodeNumber() const
593 if (_node_glob_to_loc.empty()) return 0;
594 std::set <mcIdType> keys;
595 for (INTERP_KERNEL::HashMultiMap<mcIdType, std::pair<int,mcIdType> >::const_iterator iter= _node_glob_to_loc.begin(); iter!=_node_glob_to_loc.end(); iter++)
597 keys.insert(iter->first);
599 return ToIdType(keys.size());
603 * retrieving list of nodes in global numbers
605 void ParallelTopology::getNodeList(int idomain, mcIdType *list) const
607 for (mcIdType i=0; i<_nb_nodes[idomain]; i++)
608 list[i]=_node_loc_to_glob[idomain][i];
612 * retrieving list of nodes in global numbers
614 void ParallelTopology::getCellList(int idomain, mcIdType *list) const
616 for (mcIdType i=0; i<_nb_cells[idomain];i++)
617 list[i]=_loc_to_glob[idomain][i];
620 mcIdType ParallelTopology::getFaceNumber() const
622 if (_face_glob_to_loc.empty())
624 std::set <mcIdType> keys;
625 for (INTERP_KERNEL::HashMultiMap<mcIdType, std::pair<int,mcIdType> >::const_iterator iter= _face_glob_to_loc.begin(); iter!=_face_glob_to_loc.end(); iter++)
627 keys.insert(iter->first);
629 return ToIdType(keys.size());
633 * retrieving list of faces in global numbers
635 void ParallelTopology::getFaceList(int idomain, mcIdType *list) const
637 for (mcIdType i=0; i<_nb_faces[idomain];i++)
638 list[i]=_face_loc_to_glob[idomain][i];
641 mcIdType ParallelTopology::convertGlobalFace(mcIdType iglobal, int idomain)
643 typedef INTERP_KERNEL::HashMultiMap<mcIdType, std::pair<int,mcIdType> >::const_iterator MMiter;
644 std::pair<MMiter,MMiter> eq = _face_glob_to_loc.equal_range(iglobal);
645 for (MMiter it=eq.first; it != eq.second; it++)
646 if (it->second.first == idomain)
647 return it->second.second;
651 mcIdType ParallelTopology::convertGlobalNode(mcIdType iglobal, int idomain)
653 typedef INTERP_KERNEL::HashMultiMap<mcIdType, std::pair<int,mcIdType> >::const_iterator MMiter;
654 std::pair<MMiter,MMiter> eq = _node_glob_to_loc.equal_range(iglobal);
655 for (MMiter it=eq.first; it != eq.second; it++)
657 if (it->second.first == idomain)
658 return it->second.second;
663 std::vector<MEDPARTITIONER::ConnectZone*>& ParallelTopology::getCZ()
665 return _connect_zones;
669 * adding a face to the topology
671 void ParallelTopology::appendFace(int idomain, mcIdType ilocal, mcIdType iglobal)
673 _face_loc_to_glob[idomain].push_back(iglobal);
674 _face_glob_to_loc.insert(std::make_pair(iglobal,std::make_pair(idomain,ilocal)));