KratosMultiphysics
KRATOS Multiphysics (Kratos) is a framework for building parallel, multi-disciplinary simulation software, aiming at modularity, extensibility, and high performance. Kratos is written in C++, and counts with an extensive Python interface.
distributed_sparse_graph.h
Go to the documentation of this file.
1 // | / |
2 // ' / __| _` | __| _ \ __|
3 // . \ | ( | | ( |\__ `
4 // _|\_\_| \__,_|\__|\___/ ____/
5 // Multi-Physics
6 //
7 // License: BSD License
8 // Kratos default license: kratos/license.txt
9 //
10 // Main authors: Riccardo Rossi
11 //
12 
13 #pragma once
14 
15 // System includes
16 #include <iostream>
17 #include <mutex>
19 #include "includes/serializer.h"
26 
27 // External includes
28 #include <unordered_map>
29 #include <unordered_set>
30 
31 // Project includes
32 #include "includes/define.h"
33 
34 
35 namespace Kratos
36 {
39 
42 
46 
50 
54 
58 
60 //class to construct and store a matrix graph. Can be used to construct efficiently a CSR matrix (or other sparse matrix types)
61 
66 template< class TIndexType=std::size_t >
68 {
69 public:
72  typedef TIndexType IndexType;
73  typedef int MpiIndexType;
74  typedef SparseContiguousRowGraph<IndexType> LocalGraphType; //using a map since we need it ordered
75  typedef SparseGraph<IndexType> NonLocalGraphType; //using a map since we need it ordered
76 
79 
83 
86  DataCommunicator& rComm)
87  :
88  mpComm(&rComm),
89  mLocalGraph(LocalSize)
90  {
91  mNonLocalGraphs.resize(mpComm->Size(),false);
92  mNonLocalLocks = decltype(mNonLocalLocks)(mpComm->Size());
93 
94  mpRowNumbering = Kratos::make_unique<DistributedNumbering<IndexType>>(*mpComm,LocalSize);
95  }
96 
97 
100 
101  inline const DataCommunicator& GetComm() const
102  {
103  return *mpComm;
104  }
105 
106  inline const DataCommunicator* pGetComm() const
107  {
108  return mpComm;
109  }
110 
112  {
113  return *mpRowNumbering;
114  }
115 
116  inline IndexType Size() const
117  {
118  return mpRowNumbering->Size();
119  }
120 
121  inline IndexType LocalSize() const
122  {
123  return mpRowNumbering->LocalSize();
124  }
125 
126  bool Has(const IndexType GlobalI, const IndexType GlobalJ) const
127  {
128  return mLocalGraph.Has(GetRowNumbering().LocalId(GlobalI),GlobalJ);
129  }
130 
131  //this function detects the maximum and minimum globalJ found in the local graph
133  {
134  rMaxJ = 0;
135  rMinJ = 0;
136  for(IndexType local_i = 0; local_i<mLocalGraph.Size(); ++local_i)
137  {
138  for(auto J : mLocalGraph[local_i] ) //J here is the global index
139  {
140  rMaxJ = std::max(rMaxJ, J);
141  rMinJ = std::min(rMinJ, J);
142  }
143  }
144  }
145 
147  {
148  IndexType MinJ, MaxJ;
150  return GetComm().MaxAll(MaxJ);
151  }
152 
153 
157  const typename LocalGraphType::GraphType::value_type& operator[](const IndexType& LocalPosition) const
158  {
159  return mLocalGraph[LocalPosition];
160  }
161 
162  void Clear()
163  {
164  mLocalGraph.Clear();
165  mNonLocalGraphs.clear();
166  }
167 
168  void AddEntry(const IndexType RowIndex, const IndexType ColIndex)
169  {
170  if(GetRowNumbering().IsLocal(RowIndex))
171  {
172  mLocalGraph.AddEntry(GetRowNumbering().LocalId(RowIndex), ColIndex);
173  }
174  else
175  {
176  IndexType owner = GetRowNumbering().OwnerRank(RowIndex);
177  const std::lock_guard<LockObject> scope_lock(mNonLocalLocks[owner]);
178  mNonLocalGraphs[owner].AddEntry(GetRowNumbering().RemoteLocalId(RowIndex,owner), ColIndex);
179  }
180  }
181 
182  template<class TContainerType>
183  void AddEntries(const IndexType RowIndex, const TContainerType& rColIndices)
184  {
185  if(GetRowNumbering().IsLocal(RowIndex))
186  {
187  mLocalGraph.AddEntries(GetRowNumbering().LocalId(RowIndex), rColIndices);
188  }
189  else
190  {
191  IndexType owner = GetRowNumbering().OwnerRank(RowIndex);
192  mNonLocalLocks[owner].lock();
193  mNonLocalGraphs[owner].AddEntries(GetRowNumbering().RemoteLocalId(RowIndex,owner), rColIndices);
194  mNonLocalLocks[owner].unlock();
195  }
196  }
197 
198  template<class TIteratorType>
199  void AddEntries(const IndexType RowIndex,
200  const TIteratorType& rColBegin,
201  const TIteratorType& rColEnd
202  )
203  {
204  if(GetRowNumbering().IsLocal(RowIndex))
205  {
206  mLocalGraph.AddEntries(GetRowNumbering().LocalId(RowIndex), rColBegin, rColEnd);
207  }
208  else
209  {
210  IndexType owner = GetRowNumbering().OwnerRank(RowIndex);
211  mNonLocalLocks[owner].lock();
212  mNonLocalGraphs[owner].AddEntries(GetRowNumbering().RemoteLocalId(RowIndex,owner), rColBegin, rColEnd);
213  mNonLocalLocks[owner].unlock();
214  }
215  }
216 
217  template<class TContainerType>
218  void AddEntries(const TContainerType& rIndices)
219  {
220  for(auto I : rIndices)
221  {
222  if(GetRowNumbering().IsLocal(I))
223  {
224  mLocalGraph.AddEntries(GetRowNumbering().LocalId(I), rIndices);
225  }
226  else
227  {
228  IndexType owner = GetRowNumbering().OwnerRank(I);
229  mNonLocalLocks[owner].lock();
230  mNonLocalGraphs[owner].AddEntries(GetRowNumbering().RemoteLocalId(I,owner), rIndices);;
231  mNonLocalLocks[owner].unlock();
232  }
233  }
234  }
235 
236  template<class TContainerType>
237  void AddEntries(const TContainerType& rRowIndices, const TContainerType& rColIndices)
238  {
239  for(auto I : rRowIndices)
240  {
241  AddEntries(I, rColIndices);
242  }
243  }
244 
245  // void AddEntries(DistributedSparseGraph& rOtherGraph)
246  // {
247  // //TODO
248  // }
249 
250  void Finalize()
251  {
252  std::vector<MpiIndexType> send_list;
253 
254  for(unsigned int id = 0; id<mNonLocalGraphs.size(); ++id)
255  if( !mNonLocalGraphs[id].IsEmpty())
256  send_list.push_back(id);
257 
259 
260  //sendrecv data
261  for(auto color : colors)
262  {
263  if(color >= 0) //-1 would imply no communication
264  {
265  //TODO: this can be made nonblocking
266 
267  //using serialization
268  //const auto recv_graph = mpComm->SendRecv(mNonLocalGraphs[color], color, color);
269  // for(auto row_it=recv_graph.begin(); row_it!=recv_graph.end(); ++row_it)
270  // {
271  // auto I = row_it.GetRowIndex();
272  // mLocalGraph.AddEntries(I,*row_it);
273  // }
274 
275  //using native calls
276  auto send_single_vector_repr = mNonLocalGraphs[color].ExportSingleVectorRepresentation();
277  const auto recv_single_vector_repr = mpComm->SendRecv(send_single_vector_repr, color, color);
278  mLocalGraph.AddFromSingleVectorRepresentation(recv_single_vector_repr);
279 
280  }
281  }
282 
283  }
284 
286  {
287  return mLocalGraph;
288  }
289 
291  {
292  return mNonLocalGraphs[Rank];
293  }
294 
296  {
297  return mNonLocalGraphs;
298  }
299 
300 
304 
305 
309 
310 
314 
315 
319 
321  std::string Info() const
322  {
323  std::stringstream buffer;
324  buffer << "DistributedSparseGraph" ;
325  return buffer.str();
326  }
327 
329  void PrintInfo(std::ostream& rOStream) const
330  {
331  rOStream << "DistributedSparseGraph";
332  }
333 
335  void PrintData(std::ostream& rOStream) const {}
336 
340 
341 
343 
344 protected:
347 
348 
352 
353 
357 
358 
362 
363 
367 
368 
372 
373 
377 
378 
380 
381 private:
384 
385 
389  typename DistributedNumbering<IndexType>::UniquePointer mpRowNumbering = nullptr;
390  const DataCommunicator* mpComm;
391 
392  LocalGraphType mLocalGraph;
393  DenseVector<NonLocalGraphType> mNonLocalGraphs;
394  std::vector<LockObject> mNonLocalLocks;
395 
399  friend class Serializer;
400 
401  void save(Serializer& rSerializer) const
402  {
403  }
404 
405  void load(Serializer& rSerializer)
406  {
407  }
408 
409 
413 
414 
418 
419 
423 
424 
428 
431 
433  DistributedSparseGraph(DistributedSparseGraph const& rOther) = delete;
434 
436 
437 }; // Class DistributedSparseGraph
438 
440 
443 
444 
448 
449 
451 template<class TIndexType>
452 inline std::istream& operator >> (std::istream& rIStream,
454 {
455  return rIStream;
456 }
457 
459 template<class TIndexType>
460 inline std::ostream& operator << (std::ostream& rOStream,
462 {
463  rThis.PrintInfo(rOStream);
464  rOStream << std::endl;
465  rThis.PrintData(rOStream);
466 
467  return rOStream;
468 }
470 
472 
473 } // namespace Kratos.
PeriodicInterfaceProcess & operator=(const PeriodicInterfaceProcess &)=delete
Serial (do-nothing) version of a wrapper class for MPI communication.
Definition: data_communicator.h:318
virtual int Size() const
Get the parallel size of this DataCommunicator.
Definition: data_communicator.h:597
TObject SendRecv(const TObject &rSendObject, const int SendDestination, const int SendTag, const int RecvSource, const int RecvTag) const
Exchange data with other ranks.
Definition: data_communicator.h:492
IndexType OwnerRank(const IndexType RowIndex) const
Definition: distributed_numbering.h:200
IndexType LocalSize() const
Definition: distributed_numbering.h:161
IndexType Size() const
Definition: distributed_numbering.h:167
Short class definition.
Definition: distributed_sparse_graph.h:68
const DataCommunicator & GetComm() const
Definition: distributed_sparse_graph.h:101
const DenseVector< NonLocalGraphType > & GetNonLocalGraphs() const
Definition: distributed_sparse_graph.h:295
void Clear()
Definition: distributed_sparse_graph.h:162
void Finalize()
Definition: distributed_sparse_graph.h:250
void AddEntries(const IndexType RowIndex, const TIteratorType &rColBegin, const TIteratorType &rColEnd)
Definition: distributed_sparse_graph.h:199
SparseContiguousRowGraph< IndexType > LocalGraphType
Definition: distributed_sparse_graph.h:74
TIndexType IndexType
Definition: distributed_sparse_graph.h:72
std::string Info() const
Turn back information as a string.
Definition: distributed_sparse_graph.h:321
KRATOS_CLASS_POINTER_DEFINITION(DistributedSparseGraph)
Pointer definition of DistributedSparseGraph.
DistributedSparseGraph(const IndexType LocalSize, DataCommunicator &rComm)
constructor.
Definition: distributed_sparse_graph.h:85
int MpiIndexType
Definition: distributed_sparse_graph.h:73
IndexType Size() const
Definition: distributed_sparse_graph.h:116
SparseGraph< IndexType > NonLocalGraphType
Definition: distributed_sparse_graph.h:75
bool Has(const IndexType GlobalI, const IndexType GlobalJ) const
Definition: distributed_sparse_graph.h:126
~DistributedSparseGraph()
Destructor.
Definition: distributed_sparse_graph.h:99
const NonLocalGraphType & GetNonLocalGraph(IndexType Rank) const
Definition: distributed_sparse_graph.h:290
void AddEntry(const IndexType RowIndex, const IndexType ColIndex)
Definition: distributed_sparse_graph.h:168
const DataCommunicator * pGetComm() const
Definition: distributed_sparse_graph.h:106
IndexType ComputeMaxGlobalColumnIndex() const
Definition: distributed_sparse_graph.h:146
const DistributedNumbering< IndexType > & GetRowNumbering() const
Definition: distributed_sparse_graph.h:111
void AddEntries(const TContainerType &rRowIndices, const TContainerType &rColIndices)
Definition: distributed_sparse_graph.h:237
IndexType LocalSize() const
Definition: distributed_sparse_graph.h:121
void AddEntries(const IndexType RowIndex, const TContainerType &rColIndices)
Definition: distributed_sparse_graph.h:183
void ComputeLocalMinMaxColumnIndex(IndexType &rMinJ, IndexType &rMaxJ) const
Definition: distributed_sparse_graph.h:132
void PrintInfo(std::ostream &rOStream) const
Print information about this object.
Definition: distributed_sparse_graph.h:329
const LocalGraphType::GraphType::value_type & operator[](const IndexType &LocalPosition) const
Definition: distributed_sparse_graph.h:157
void PrintData(std::ostream &rOStream) const
Print object's data.
Definition: distributed_sparse_graph.h:335
void AddEntries(const TContainerType &rIndices)
Definition: distributed_sparse_graph.h:218
const LocalGraphType & GetLocalGraph() const
Definition: distributed_sparse_graph.h:285
Definition: amatrix_interface.h:41
TDataType value_type
Definition: amatrix_interface.h:56
static std::vector< int > ComputeCommunicationScheduling(const std::vector< int > &rLocalDestinationIds, const DataCommunicator &rComm)
Definition: communication_coloring_utilities.cpp:56
The serialization consists in storing the state of an object into a storage format like data file or ...
Definition: serializer.h:123
void Clear()
Definition: sparse_contiguous_row_graph.h:135
bool Has(const IndexType I, const IndexType J) const
Definition: sparse_contiguous_row_graph.h:145
void AddEntry(const IndexType RowIndex, const IndexType ColIndex)
Definition: sparse_contiguous_row_graph.h:164
void AddEntries(const IndexType RowIndex, const TContainerType &rColIndices)
Definition: sparse_contiguous_row_graph.h:172
IndexType Size() const
Definition: sparse_contiguous_row_graph.h:141
void AddFromSingleVectorRepresentation(const std::vector< IndexType > &rSingleVectorRepresentation)
Definition: sparse_contiguous_row_graph.h:349
Short class definition.
Definition: sparse_graph.h:66
static double max(double a, double b)
Definition: GeometryFunctions.h:79
static double min(double a, double b)
Definition: GeometryFunctions.h:71
REF: G. R. Cowper, GAUSSIAN QUADRATURE FORMULAS FOR TRIANGLES.
Definition: mesh_condition.cpp:21
std::istream & operator>>(std::istream &rIStream, LinearMasterSlaveConstraint &rThis)
input stream function
std::ostream & operator<<(std::ostream &rOStream, const LinearMasterSlaveConstraint &rThis)
output stream function
Definition: linear_master_slave_constraint.h:432
color
Definition: all_t_win_vs_m_fixed_error.py:230
Definition: colors.py:1
def load(f)
Definition: ode_solve.py:307
J
Definition: sensitivityMatrix.py:58
def IsEmpty(_A)
Definition: custom_math.py:33