mapDistribute.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 | Copyright (C) 2011-2016 OpenFOAM Foundation
6  \\/ M anipulation |
7 -------------------------------------------------------------------------------
8 License
9  This file is part of OpenFOAM.
10 
11  OpenFOAM is free software: you can redistribute it and/or modify it
12  under the terms of the GNU General Public License as published by
13  the Free Software Foundation, either version 3 of the License, or
14  (at your option) any later version.
15 
16  OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
17  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
18  FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
19  for more details.
20 
21  You should have received a copy of the GNU General Public License
22  along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
23 
24 \*---------------------------------------------------------------------------*/
25 
26 #include "mapDistribute.H"
28 #include "transformField.H"
29 
30 // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
31 
32 namespace Foam
33 {
34 defineTypeNameAndDebug(mapDistribute, 0);
35 }
36 
37 // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
38 
39 template<>
40 void Foam::mapDistribute::transform::operator()
41 (
42  const vectorTensorTransform&,
43  const bool,
45 ) const
46 {}
47 template<>
48 void Foam::mapDistribute::transform::operator()
49 (
50  const coupledPolyPatch&,
52 ) const
53 {}
54 template<>
55 void Foam::mapDistribute::transform::operator()
56 (
57  const coupledPolyPatch&,
58  Map<label>&
59 ) const
60 {}
61 template<>
62 void Foam::mapDistribute::transform::operator()
63 (
64  const coupledPolyPatch&,
66 ) const
67 {}
68 
69 
70 template<>
71 void Foam::mapDistribute::transform::operator()
72 (
73  const vectorTensorTransform&,
74  const bool,
76 ) const
77 {}
78 template<>
79 void Foam::mapDistribute::transform::operator()
80 (
81  const coupledPolyPatch&,
83 ) const
84 {}
85 template<>
86 void Foam::mapDistribute::transform::operator()
87 (
88  const coupledPolyPatch&,
90 ) const
91 {}
92 template<>
93 void Foam::mapDistribute::transform::operator()
94 (
95  const coupledPolyPatch&,
97 ) const
98 {}
99 
100 
101 template<>
102 void Foam::mapDistribute::transform::operator()
103 (
104  const vectorTensorTransform&,
105  const bool,
106  List<bool>&
107 ) const
108 {}
109 template<>
110 void Foam::mapDistribute::transform::operator()
111 (
112  const coupledPolyPatch&,
113  UList<bool>&
114 ) const
115 {}
116 template<>
117 void Foam::mapDistribute::transform::operator()
118 (
119  const coupledPolyPatch&,
120  Map<bool>&
121 ) const
122 {}
123 template<>
124 void Foam::mapDistribute::transform::operator()
125 (
126  const coupledPolyPatch&,
128 ) const
129 {}
130 
131 
133 {
135 
136  forAll(transformElements_, trafoI)
137  {
138  if (transformElements_[trafoI].size() > 0)
139  {
140  os << "transform " << trafoI << ':' << endl
141  << " start : " << transformStart_[trafoI] << endl
142  << " size : " << transformElements_[trafoI].size() << endl;
143  }
144  }
145 }
146 
147 
148 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
149 
151 :
153 {}
154 
155 
157 (
158  const label constructSize,
161  const bool subHasFlip,
162  const bool constructHasFlip
163 )
164 :
166  (
167  constructSize,
168  subMap,
169  constructMap,
170  subHasFlip,
171  constructHasFlip
172  )
173 {}
174 
175 
177 (
178  const label constructSize,
179  const Xfer<labelListList>& subMap,
180  const Xfer<labelListList>& constructMap,
183  const bool subHasFlip,
184  const bool constructHasFlip
185 )
186 :
188  (
189  constructSize,
190  subMap,
191  constructMap,
192  subHasFlip,
193  constructHasFlip
194  ),
195  transformElements_(transformElements),
196  transformStart_(transformStart)
197 {}
198 
199 
201 (
202  const labelList& sendProcs,
203  const labelList& recvProcs
204 )
205 :
206  mapDistributeBase(sendProcs, recvProcs)
207 {}
208 
209 
211 (
212  const globalIndex& globalNumbering,
213  labelList& elements,
214  List<Map<label>>& compactMap,
215  const int tag
216 )
217 :
219  (
220  globalNumbering,
221  elements,
222  compactMap,
223  tag
224  )
225 {}
226 
227 
229 (
230  const globalIndex& globalNumbering,
231  labelListList& cellCells,
232  List<Map<label>>& compactMap,
233  const int tag
234 )
235 :
237  (
238  globalNumbering,
239  cellCells,
240  compactMap,
241  tag
242  )
243 {}
244 
245 
247 (
248  const globalIndex& globalNumbering,
249  labelList& elements,
250  const globalIndexAndTransform& globalTransforms,
251  const labelPairList& transformedElements,
252  labelList& transformedIndices,
253  List<Map<label>>& compactMap,
254  const int tag
255 )
256 :
258 {
259  // Construct per processor compact addressing of the global elements
260  // needed. The ones from the local processor are not included since
261  // these are always all needed.
263  (
264  globalNumbering,
265  elements,
266  compactMap
267  );
268 
269  // Add all (non-local) transformed elements needed.
270  forAll(transformedElements, i)
271  {
272  labelPair elem = transformedElements[i];
274  if (proci != Pstream::myProcNo())
275  {
277  label nCompact = compactMap[proci].size();
278  compactMap[proci].insert(index, nCompact);
279  }
280  }
281 
282 
283  // Exchange what I need with processor that supplies it. Renumber elements
284  // into compact numbering
285  labelList compactStart;
287  (
288  tag,
289  globalNumbering,
290  elements,
291  compactMap,
292  compactStart
293  );
294 
295 
296  // Renumber the transformed elements
297  // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
298  // Count per transformIndex
299  label nTrafo = globalTransforms.transformPermutations().size();
300  labelList nPerTransform(nTrafo, 0);
301  forAll(transformedElements, i)
302  {
303  labelPair elem = transformedElements[i];
305  nPerTransform[trafoI]++;
306  }
307  // Offset per transformIndex
308  transformStart_.setSize(nTrafo);
309  transformElements_.setSize(nTrafo);
310  forAll(transformStart_, trafoI)
311  {
312  transformStart_[trafoI] = constructSize_;
313  constructSize_ += nPerTransform[trafoI];
314  transformElements_[trafoI].setSize(nPerTransform[trafoI]);
315  }
316 
317  // Sort transformed elements into their new slot.
318  nPerTransform = 0;
319 
320  transformedIndices.setSize(transformedElements.size());
321  forAll(transformedElements, i)
322  {
323  labelPair elem = transformedElements[i];
327 
328  // Get compact index for untransformed element
329  label rawElemI =
330  (
331  proci == Pstream::myProcNo()
332  ? index
333  : compactMap[proci][index]
334  );
335 
336  label& n = nPerTransform[trafoI];
337  // index of element to transform
338  transformElements_[trafoI][n] = rawElemI;
339  // destination of transformed element
340  transformedIndices[i] = transformStart_[trafoI]+n;
341  n++;
342  }
343 
344  if (debug)
345  {
346  printLayout(Pout);
347  }
348 }
349 
350 
352 (
353  const globalIndex& globalNumbering,
354  labelListList& cellCells,
355  const globalIndexAndTransform& globalTransforms,
356  const List<labelPairList>& transformedElements,
357  labelListList& transformedIndices,
358  List<Map<label>>& compactMap,
359  const int tag
360 )
361 :
363 {
364  // Construct per processor compact addressing of the global elements
365  // needed. The ones from the local processor are not included since
366  // these are always all needed.
368  (
369  globalNumbering,
370  cellCells,
371  compactMap
372  );
373 
374  // Add all (non-local) transformed elements needed.
375  forAll(transformedElements, celli)
376  {
377  const labelPairList& elems = transformedElements[celli];
378 
379  forAll(elems, i)
380  {
381  label proci = globalIndexAndTransform::processor(elems[i]);
382  if (proci != Pstream::myProcNo())
383  {
384  label index = globalIndexAndTransform::index(elems[i]);
385  label nCompact = compactMap[proci].size();
386  compactMap[proci].insert(index, nCompact);
387  }
388  }
389  }
390 
391 
392  // Exchange what I need with processor that supplies it. Renumber elements
393  // into compact numbering
394  labelList compactStart;
396  (
397  tag,
398  globalNumbering,
399  cellCells,
400  compactMap,
401  compactStart
402  );
403 
404 
405  // Renumber the transformed elements
406  // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
407  // Count per transformIndex
408  label nTrafo = globalTransforms.transformPermutations().size();
409  labelList nPerTransform(nTrafo, 0);
410  forAll(transformedElements, celli)
411  {
412  const labelPairList& elems = transformedElements[celli];
413 
414  forAll(elems, i)
415  {
417  nPerTransform[trafoI]++;
418  }
419  }
420  // Offset per transformIndex
421  transformStart_.setSize(nTrafo);
422  transformElements_.setSize(nTrafo);
423  forAll(transformStart_, trafoI)
424  {
425  transformStart_[trafoI] = constructSize_;
426  constructSize_ += nPerTransform[trafoI];
427  transformElements_[trafoI].setSize(nPerTransform[trafoI]);
428  }
429 
430  // Sort transformed elements into their new slot.
431  nPerTransform = 0;
432 
433  transformedIndices.setSize(transformedElements.size());
434  forAll(transformedElements, celli)
435  {
436  const labelPairList& elems = transformedElements[celli];
437  transformedIndices[celli].setSize(elems.size());
438 
439  forAll(elems, i)
440  {
441  label proci = globalIndexAndTransform::processor(elems[i]);
442  label index = globalIndexAndTransform::index(elems[i]);
444 
445  // Get compact index for untransformed element
446  label rawElemI =
447  (
448  proci == Pstream::myProcNo()
449  ? index
450  : compactMap[proci][index]
451  );
452 
453  label& n = nPerTransform[trafoI];
454  // index of element to transform
455  transformElements_[trafoI][n] = rawElemI;
456  // destination of transformed element
457  transformedIndices[celli][i] = transformStart_[trafoI]+n;
458  n++;
459  }
460  }
461 
462  if (debug)
463  {
464  printLayout(Pout);
465  }
466 }
467 
468 
470 :
471  mapDistributeBase(map),
472  transformElements_(map.transformElements_),
473  transformStart_(map.transformStart_)
474 {}
475 
476 
478 :
480  (
481  map().constructSize_,
482  map().subMap_.xfer(),
483  map().constructMap_.xfer(),
484  map().subHasFlip(),
485  map().constructHasFlip()
486  ),
487  transformElements_(map().transformElements_.xfer()),
488  transformStart_(map().transformStart_.xfer())
489 {}
490 
491 
493 {
494  is >> *this;
495 }
496 
497 
499 {
500  return autoPtr<mapDistribute>(new mapDistribute(*this));
501 }
502 
503 
504 // * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * * //
505 
507 const
508 {
509  return findLower(transformStart_, index+1);
510 }
511 
512 
514 {
516  transformElements_.transfer(rhs.transformElements_);
517  transformStart_.transfer(rhs.transformStart_);
518 }
519 
520 
522 {
523  return xferMove(*this);
524 }
525 
526 
527 // * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * //
528 
530 {
531  // Check for assignment to self
532  if (this == &rhs)
533  {
535  << "Attempted assignment to self"
536  << abort(FatalError);
537  }
539  transformElements_ = rhs.transformElements_;
540  transformStart_ = rhs.transformStart_;
541 }
542 
543 
544 // * * * * * * * * * * * * * * Istream Operator * * * * * * * * * * * * * * //
545 
547 {
548  is.fatalCheck("operator>>(Istream&, mapDistribute&)");
549 
550  is >> static_cast<mapDistributeBase&>(map)
551  >> map.transformElements_ >> map.transformStart_;
552 
553  return is;
554 }
555 
556 
557 // * * * * * * * * * * * * * * Ostream Operator * * * * * * * * * * * * * * //
558 
560 {
561  os << static_cast<const mapDistributeBase&>(map) << token::NL
562  << map.transformElements_ << token::NL
563  << map.transformStart_;
564 
565  return os;
566 }
567 
568 
569 // ************************************************************************* //
A simple container for copying or transferring objects of type <T>.
Definition: Xfer.H:85
autoPtr< mapDistribute > clone() const
Clone.
#define forAll(list, i)
Loop across all elements in list.
Definition: UList.H:428
intWM_LABEL_SIZE_t label
A label is an int32_t or int64_t as specified by the pre-processor macro WM_LABEL_SIZE.
Definition: label.H:59
void printLayout(Ostream &os) const
Debug: print layout. Can only be used on maps with sorted.
const labelListList & constructMap() const
From subsetted data to new reconstructed data.
const labelList & transformStart() const
Destination in constructMap for transformed elements.
error FatalError
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
Definition: error.H:319
Vector-tensor class used to perform translations and rotations in 3D space.
const labelListList & subMap() const
From subsetted data back to original data.
An Istream is an abstract base class for all input systems (streams, files, token lists etc)...
Definition: Istream.H:57
void size(const label)
Override size to be inconsistent with allocated storage.
Definition: ListI.H:76
labelListList subMap_
Maps from subsetted data back to original data.
static label processor(const labelPair &globalIAndTransform)
Which processor does this come from?
static int myProcNo(const label communicator=0)
Number of this process (starting from masterNo() = 0)
Definition: UPstream.H:417
static label index(const labelPair &globalIAndTransform)
Index carried by the object.
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:253
bool constructHasFlip() const
Does constructMap include a sign.
bool subHasFlip() const
Does subMap include a sign.
The coupledPolyPatch is an abstract base class for patches that couple regions of the computational d...
void transfer(mapDistribute &)
Transfer the contents of the argument and annul the argument.
mapDistributeBase()
Construct null.
label constructSize_
Size of reconstructed data.
const List< vectorTensorTransform > & transformPermutations() const
Return access to the permuted transforms.
Spatial transformation functions for primitive fields.
Calculates a unique integer (label so might not have enough room - 2G max) for processor + local inde...
Definition: globalIndex.H:63
An ordered pair of two objects of type <T> with first() and second() elements.
Definition: contiguous.H:49
void printLayout(Ostream &os) const
Debug: print layout. Can only be used on maps with sorted.
Xfer< T > xferMove(T &)
Construct by transferring the contents of the arg.
void operator=(const mapDistribute &)
Istream & operator>>(Istream &, directionInfo &)
errorManip< error > abort(error &err)
Definition: errorManip.H:131
labelListList constructMap_
Maps from subsetted data to new reconstructed data.
A 1D vector of objects of type <T>, where the size of the vector is known and can be used for subscri...
Definition: HashTable.H:60
void operator=(const mapDistributeBase &)
mapDistribute()
Construct null.
Class containing processor-to-processor mapping information.
An Ostream is an abstract base class for all output systems (streams, files, token lists...
Definition: Ostream.H:53
prefixOSstream Pout(cout,"Pout")
Definition: IOstreams.H:53
defineTypeNameAndDebug(combustionModel, 0)
void calcCompactAddressing(const globalIndex &globalNumbering, const labelList &elements, List< Map< label >> &compactMap) const
Construct per processor compact addressing of the global elements.
void setSize(const label)
Reset size of List.
Definition: List.C:295
Class containing processor-to-processor mapping information.
void exchangeAddressing(const int tag, const globalIndex &globalNumbering, labelList &elements, List< Map< label >> &compactMap, labelList &compactStart)
label whichTransform(const label index) const
Find transform from transformElements.
Ostream & operator<<(Ostream &, const ensightPart &)
const labelListList & transformElements() const
For every globalIndexAndTransform::transformPermutations.
label findLower(const ListType &, typename ListType::const_reference, const label stary, const BinaryOp &bop)
Find last element < given value in sorted list and return index,.
label n
Xfer< mapDistribute > xfer()
Transfer contents to the Xfer container.
void transfer(mapDistributeBase &)
Transfer the contents of the argument and annul the argument.
static label transformIndex(const labelPair &globalIAndTransform)
Transform carried by the object.
label constructSize() const
Constructed data size.
void transfer(List< T > &)
Transfer the contents of the argument List into this list.
Definition: List.C:365
void fatalCheck(const char *operation) const
Check IOstream status for given operation.
Definition: IOstream.C:105
Namespace for OpenFOAM.
Determination and storage of the possible independent transforms introduced by coupledPolyPatches, as well as all of the possible permutations of these transforms generated by the presence of multiple coupledPolyPatches, i.e. more than one cyclic boundary.