metisLikeDecomp.C
Go to the documentation of this file.
1 /*---------------------------------------------------------------------------*\
2  ========= |
3  \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
4  \\ / O peration |
5  \\ / A nd | www.openfoam.com
6  \\/ M anipulation |
7 -------------------------------------------------------------------------------
8  Copyright (C) 2017-2020 OpenCFD Ltd.
9 -------------------------------------------------------------------------------
10 License
11  This file is part of OpenFOAM.
12 
13  OpenFOAM is free software: you can redistribute it and/or modify it
14  under the terms of the GNU General Public License as published by
15  the Free Software Foundation, either version 3 of the License, or
16  (at your option) any later version.
17 
18  OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
19  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
20  FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
21  for more details.
22 
23  You should have received a copy of the GNU General Public License
24  along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
25 
26 \*---------------------------------------------------------------------------*/
27 
28 #include "metisLikeDecomp.H"
29 #include "Time.H"
30 #include "globalIndex.H"
31 
32 // * * * * * * * * * * * * Protected Member Functions * * * * * * * * * * * //
33 
35 (
36  const labelList& adjncy,
37  const labelList& xadj,
38  const List<scalar>& cWeights,
39  labelList& decomp
40 ) const
41 {
42  if (!Pstream::parRun())
43  {
44  return decomposeSerial
45  (
46  adjncy,
47  xadj,
48  cWeights,
49  decomp
50  );
51  }
52 
53  if (debug)
54  {
55  Info<< type() << "Decomp : running in parallel."
56  << " Decomposing all of graph on master processor." << endl;
57  }
58  globalIndex globalCells(xadj.size()-1);
59  label nTotalConnections = returnReduce(adjncy.size(), sumOp<label>());
60 
61  // Send all to master. Use scheduled to save some storage.
62  if (Pstream::master())
63  {
64  List<label> allAdjncy(nTotalConnections);
65  List<label> allXadj(globalCells.size()+1);
66  List<scalar> allWeights(globalCells.size());
67 
68  // Insert my own
69  label nTotalCells = 0;
70  forAll(cWeights, celli)
71  {
72  allXadj[nTotalCells] = xadj[celli];
73  allWeights[nTotalCells++] = cWeights[celli];
74  }
75  nTotalConnections = 0;
76  forAll(adjncy, i)
77  {
78  allAdjncy[nTotalConnections++] = adjncy[i];
79  }
80 
81  for (const int slave : Pstream::subProcs())
82  {
83  IPstream fromSlave(Pstream::commsTypes::scheduled, slave);
84  List<label> nbrAdjncy(fromSlave);
85  List<label> nbrXadj(fromSlave);
86  List<scalar> nbrWeights(fromSlave);
87 
88  // Append.
89  forAll(nbrXadj, celli)
90  {
91  allXadj[nTotalCells] = nTotalConnections+nbrXadj[celli];
92  allWeights[nTotalCells++] = nbrWeights[celli];
93  }
94  // No need to renumber xadj since already global.
95  forAll(nbrAdjncy, i)
96  {
97  allAdjncy[nTotalConnections++] = nbrAdjncy[i];
98  }
99  }
100  allXadj[nTotalCells] = nTotalConnections;
101 
102  labelList allDecomp;
103  decomposeSerial
104  (
105  allAdjncy,
106  allXadj,
107  allWeights,
108  allDecomp
109  );
110 
111 
112  // Send allFinalDecomp back
113  for (const int slave : Pstream::subProcs())
114  {
115  OPstream toSlave(Pstream::commsTypes::scheduled, slave);
116  toSlave << SubList<label>
117  (
118  allDecomp,
119  globalCells.localSize(slave),
120  globalCells.offset(slave)
121  );
122  }
123 
124  // Get my own part (always first)
125  decomp = SubList<label>(allDecomp, globalCells.localSize());
126  }
127  else
128  {
129  // Send my part of the graph (already in global numbering)
130  {
131  OPstream toMaster
132  (
133  Pstream::commsTypes::scheduled,
134  Pstream::masterNo()
135  );
136  toMaster
137  << adjncy
138  << SubList<label>(xadj, xadj.size()-1)
139  << cWeights;
140  }
141 
142  // Receive back decomposition
143  IPstream fromMaster
144  (
145  Pstream::commsTypes::scheduled,
146  Pstream::masterNo()
147  );
148  fromMaster >> decomp;
149  }
150 
151  return 0;
152 }
153 
154 
155 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
156 
158 (
159  const word& derivedType,
160  const dictionary& decompDict,
161  int select
162 )
163 :
164  decompositionMethod(decompDict),
165  coeffsDict_(findCoeffsDict(derivedType + "Coeffs", select))
166 {}
167 
168 
170 (
171  const word& derivedType,
172  const dictionary& decompDict,
173  const word& regionName,
174  int select
175 )
176 :
177  decompositionMethod(decompDict, regionName),
178  coeffsDict_(findCoeffsDict(derivedType + "Coeffs", select))
179 {}
180 
181 
182 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
183 
185 (
186  const polyMesh& mesh,
187  const pointField& points,
188  const scalarField& pointWeights
189 ) const
190 {
191  if (points.size() != mesh.nCells())
192  {
194  << "Can use this decomposition method only for entire mesh" << nl
195  << "and supply one coordinate (cellCentre) for every cell." << nl
196  << "The number of coordinates " << points.size() << nl
197  << "The number of cells in the mesh " << mesh.nCells()
198  << exit(FatalError);
199  }
200 
201  CompactListList<label> cellCells;
202  calcCellCells
203  (
204  mesh,
205  identity(mesh.nCells()),
206  mesh.nCells(),
207  true,
208  cellCells
209  );
210 
211  // Decompose using default weights
212  labelList decomp;
213  decomposeGeneral(cellCells.m(), cellCells.offsets(), pointWeights, decomp);
214 
215  return decomp;
216 }
217 
218 
220 (
221  const polyMesh& mesh,
222  const labelList& agglom,
223  const pointField& agglomPoints,
224  const scalarField& agglomWeights
225 ) const
226 {
227  if (agglom.size() != mesh.nCells())
228  {
230  << "Size of cell-to-coarse map " << agglom.size()
231  << " differs from number of cells in mesh " << mesh.nCells()
232  << exit(FatalError);
233  }
234 
235  // Make Metis CSR (Compressed Storage Format) storage
236  // adjncy : contains neighbours (= edges in graph)
237  // xadj(celli) : start of information in adjncy for celli
238 
239  CompactListList<label> cellCells;
240  calcCellCells
241  (
242  mesh,
243  agglom,
244  agglomPoints.size(),
245  true,
246  cellCells
247  );
248 
249  // Decompose using default weights
250  labelList decomp;
251  decomposeGeneral(cellCells.m(), cellCells.offsets(), agglomWeights, decomp);
252 
253 
254  // Rework back into decomposition for original mesh
255  labelList fineDistribution(agglom.size());
256 
257  forAll(fineDistribution, i)
258  {
259  fineDistribution[i] = decomp[agglom[i]];
260  }
261 
262  return fineDistribution;
263 }
264 
265 
267 (
268  const labelListList& globalCellCells,
269  const pointField& cellCentres,
270  const scalarField& cellWeights
271 ) const
272 {
273  if (cellCentres.size() != globalCellCells.size())
274  {
276  << "Inconsistent number of cells (" << globalCellCells.size()
277  << ") and number of cell centres (" << cellCentres.size()
278  << ")." << exit(FatalError);
279  }
280 
281  // Make Metis CSR (Compressed Storage Format) storage
282  // adjncy : contains neighbours (= edges in graph)
283  // xadj(celli) : start of information in adjncy for celli
284 
285  CompactListList<label> cellCells(globalCellCells);
286 
287  // Decompose using default weights
288  labelList decomp;
289  decomposeGeneral(cellCells.m(), cellCells.offsets(), cellWeights, decomp);
290 
291  return decomp;
292 }
293 
294 // ************************************************************************* //
Foam::CompactListList::offsets
const List< label > & offsets() const
Return the offset table (= size()+1)
Definition: CompactListListI.H:142
Foam::expressions::patchExpr::debug
int debug
Static debugging option.
Foam::CompactListList::m
const List< T > & m() const
Return the packed matrix of data.
Definition: CompactListListI.H:156
Foam::word
A class for handling words, derived from Foam::string.
Definition: word.H:62
Foam::metisLikeDecomp::decomposeGeneral
virtual label decomposeGeneral(const labelList &adjncy, const labelList &xadj, const List< scalar > &cellWeights, labelList &decomp) const
Serial and/or collect/distribute for parallel operation.
Definition: metisLikeDecomp.C:35
Foam::returnReduce
T returnReduce(const T &Value, const BinaryOp &bop, const int tag=Pstream::msgType(), const label comm=UPstream::worldComm)
Definition: PstreamReduceOps.H:94
Foam::OPstream
Output inter-processor communications stream.
Definition: OPstream.H:52
Foam::SubList
A List obtained as a section of another List.
Definition: SubList.H:53
Foam::CompactListList
A packed storage unstructured matrix of objects of type <T> using an offset table for access.
Definition: polyTopoChange.H:93
globalIndex.H
Foam::endl
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:350
Foam::polyMesh
Mesh consisting of general polyhedral cells.
Definition: polyMesh.H:77
Foam::sumOp
Definition: ops.H:213
forAll
#define forAll(list, i)
Loop across all elements in list.
Definition: stdFoam.H:296
regionName
Foam::word regionName
Definition: createNamedDynamicFvMesh.H:1
Foam::Field< vector >
Foam::Info
messageStream Info
Information stream (uses stdout - output is on the master only)
Foam::FatalError
error FatalError
Foam::dictionary
A list of keyword definitions, which are a keyword followed by a number of values (eg,...
Definition: dictionary.H:121
mesh
dynamicFvMesh & mesh
Definition: createDynamicFvMesh.H:6
Foam::decompositionMethod
Abstract base class for domain decomposition.
Definition: decompositionMethod.H:51
Foam::globalIndex
Calculates a unique integer (label so might not have enough room - 2G max) for processor + local inde...
Definition: globalIndex.H:68
Foam::exit
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition: errorManip.H:130
Foam::metisLikeDecomp::decompose
virtual labelList decompose(const polyMesh &mesh, const pointField &points, const scalarField &pointWeights) const
Return for every coordinate the wanted processor number.
Definition: metisLikeDecomp.C:185
Time.H
FatalErrorInFunction
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
Definition: error.H:381
metisLikeDecomp.H
Foam::nl
constexpr char nl
Definition: Ostream.H:385
Foam::List< label >
Foam::metisLikeDecomp::metisLikeDecomp
metisLikeDecomp(const metisLikeDecomp &)=delete
No copy construct.
points
const pointField & points
Definition: gmvOutputHeader.H:1
Foam::identity
labelList identity(const label len, label start=0)
Create identity map of the given length with (map[i] == i)
Definition: labelList.C:38
Foam::roots::type
type
Types of root.
Definition: Roots.H:54
Foam::IPstream
Input inter-processor communications stream.
Definition: IPstream.H:52