faceZone.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) 2011-2016 OpenFOAM Foundation
9 Copyright (C) 2017-2021 OpenCFD Ltd.
10-------------------------------------------------------------------------------
11License
12 This file is part of OpenFOAM.
13
14 OpenFOAM is free software: you can redistribute it and/or modify it
15 under the terms of the GNU General Public License as published by
16 the Free Software Foundation, either version 3 of the License, or
17 (at your option) any later version.
18
19 OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
20 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
21 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
22 for more details.
23
24 You should have received a copy of the GNU General Public License
25 along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
26
27\*---------------------------------------------------------------------------*/
28
29#include "faceZone.H"
31#include "faceZoneMesh.H"
32#include "polyMesh.H"
33#include "primitiveMesh.H"
34#include "demandDrivenData.H"
35#include "mapPolyMesh.H"
36#include "syncTools.H"
37
38// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
39
40namespace Foam
41{
45}
46
47const char* const Foam::faceZone::labelsName = "faceLabels";
48
49
50// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
51
52void Foam::faceZone::setFlipMap(const bool val)
53{
54 // Match size for flipMap
55 if (flipMap_.size() == this->size())
56 {
57 flipMap_ = val;
58 }
59 else
60 {
61 // Avoid copying old values on resize
62 flipMap_.clear();
63 flipMap_.resize(this->size(), val);
64 }
65}
66
67
68// * * * * * * * * * * * * Protected Member Functions * * * * * * * * * * * //
69
70void Foam::faceZone::calcFaceZonePatch() const
71{
72 DebugInFunction << "Calculating primitive patch" << endl;
73
74 if (patchPtr_)
75 {
77 << "primitive face zone patch already calculated"
78 << abort(FatalError);
79 }
80
81 patchPtr_ =
83 (
84 faceList(size()),
85 zoneMesh().mesh().points()
86 );
87
88 primitiveFacePatch& patch = *patchPtr_;
89
90 const faceList& f = zoneMesh().mesh().faces();
91
92 const labelList& addr = *this;
93 const boolList& flip = flipMap();
94
95 forAll(addr, facei)
96 {
97 if (flip[facei])
98 {
99 patch[facei] = f[addr[facei]].reverseFace();
100 }
101 else
102 {
103 patch[facei] = f[addr[facei]];
104 }
105 }
106
107 DebugInfo << "Finished calculating primitive patch" << endl;
108}
109
110
111void Foam::faceZone::calcCellLayers() const
112{
113 DebugInFunction << "Calculating master cells" << endl;
114
115 // It is an error to attempt to recalculate edgeCells
116 // if the pointer is already set
117 if (masterCellsPtr_ || slaveCellsPtr_)
118 {
120 << "cell layers already calculated"
121 << abort(FatalError);
122 }
123 else
124 {
125 // Go through all the faces in the master zone. Choose the
126 // master or slave cell based on the face flip
127
128 const labelList& own = zoneMesh().mesh().faceOwner();
129 const labelList& nei = zoneMesh().mesh().faceNeighbour();
130
131 const labelList& mf = *this;
132
133 const boolList& faceFlip = flipMap();
134
135 masterCellsPtr_ = new labelList(mf.size());
136 labelList& mc = *masterCellsPtr_;
137
138 slaveCellsPtr_ = new labelList(mf.size());
139 labelList& sc = *slaveCellsPtr_;
140
141 forAll(mf, facei)
142 {
143 const label ownCelli = own[mf[facei]];
144 const label neiCelli =
145 (
146 zoneMesh().mesh().isInternalFace(mf[facei])
147 ? nei[mf[facei]]
148 : -1
149 );
150
151 if (!faceFlip[facei])
152 {
153 // Face is oriented correctly, no flip needed
154 mc[facei] = neiCelli;
155 sc[facei] = ownCelli;
156 }
157 else
158 {
159 mc[facei] = ownCelli;
160 sc[facei] = neiCelli;
161 }
162 }
163 }
164}
165
166
167void Foam::faceZone::checkAddressing() const
168{
169 const labelList& addr = *this;
170
171 if (addr.size() != flipMap_.size())
172 {
174 << "Size of addressing: " << addr.size()
175 << " size of flip map: " << flipMap_.size()
176 << abort(FatalError);
177 }
178
179 // Note: nFaces, nCells might not be set yet on mesh so use owner size
180 const label nFaces = zoneMesh().mesh().faceOwner().size();
181
182 for (const label facei : addr)
183 {
184 if (facei < 0 || facei >= nFaces)
185 {
187 << "Illegal face index " << facei
188 << " outside range 0.." << nFaces-1 << endl;
189 break; // Only report once
190 }
191 }
192}
193
194
195// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
196
198(
199 const word& name,
200 const label index,
201 const faceZoneMesh& zm
202)
203:
204 zone(name, index),
205 flipMap_(),
206 zoneMesh_(zm),
207 patchPtr_(nullptr),
208 masterCellsPtr_(nullptr),
209 slaveCellsPtr_(nullptr),
210 mePtr_(nullptr)
211{}
212
213
215(
216 const word& name,
217 const labelUList& addr,
218 const bool flipMapValue,
219 const label index,
220 const faceZoneMesh& zm
221)
222:
223 zone(name, addr, index),
224 flipMap_(),
225 zoneMesh_(zm),
226 patchPtr_(nullptr),
227 masterCellsPtr_(nullptr),
228 slaveCellsPtr_(nullptr),
229 mePtr_(nullptr)
230{
231 flipMap_.resize(size(), flipMapValue);
232 checkAddressing();
233}
234
235
237(
238 const word& name,
239 labelList&& addr,
240 const bool flipMapValue,
241 const label index,
242 const faceZoneMesh& zm
243)
244:
245 zone(name, std::move(addr), index),
246 flipMap_(),
247 zoneMesh_(zm),
248 patchPtr_(nullptr),
249 masterCellsPtr_(nullptr),
250 slaveCellsPtr_(nullptr),
251 mePtr_(nullptr)
252{
253 flipMap_.resize(size(), flipMapValue);
254 checkAddressing();
255}
256
257
259(
260 const word& name,
261 const labelUList& addr,
262 const boolUList& fm,
263 const label index,
264 const faceZoneMesh& zm
265)
266:
267 zone(name, addr, index),
268 flipMap_(fm),
269 zoneMesh_(zm),
270 patchPtr_(nullptr),
271 masterCellsPtr_(nullptr),
272 slaveCellsPtr_(nullptr),
273 mePtr_(nullptr)
274{
275 checkAddressing();
276}
277
278
280(
281 const word& name,
282 labelList&& addr,
283 boolList&& fm,
284 const label index,
285 const faceZoneMesh& zm
286)
287:
288 zone(name, std::move(addr), index),
289 flipMap_(std::move(fm)),
290 zoneMesh_(zm),
291 patchPtr_(nullptr),
292 masterCellsPtr_(nullptr),
293 slaveCellsPtr_(nullptr),
294 mePtr_(nullptr)
295{
296 checkAddressing();
297}
298
299
301(
302 const word& name,
303 const dictionary& dict,
304 const label index,
305 const faceZoneMesh& zm
306)
307:
308 zone(name, dict, this->labelsName, index),
309 flipMap_(dict.lookup("flipMap")),
310 zoneMesh_(zm),
311 patchPtr_(nullptr),
312 masterCellsPtr_(nullptr),
313 slaveCellsPtr_(nullptr),
314 mePtr_(nullptr)
315{
316 checkAddressing();
317}
318
319
321(
322 const faceZone& origZone,
323 const labelUList& addr,
324 const boolUList& fm,
325 const label index,
326 const faceZoneMesh& zm
327)
328:
329 zone(origZone, addr, index),
330 flipMap_(fm),
331 zoneMesh_(zm),
332 patchPtr_(nullptr),
333 masterCellsPtr_(nullptr),
334 slaveCellsPtr_(nullptr),
335 mePtr_(nullptr)
336{
337 checkAddressing();
338}
339
340
342(
343 const faceZone& origZone,
344 labelList&& addr,
345 boolList&& fm,
346 const label index,
347 const faceZoneMesh& zm
348)
349:
350 zone(origZone, std::move(addr), index),
351 flipMap_(std::move(fm)),
352 zoneMesh_(zm),
353 patchPtr_(nullptr),
354 masterCellsPtr_(nullptr),
355 slaveCellsPtr_(nullptr),
356 mePtr_(nullptr)
357{
358 checkAddressing();
359}
360
361
362// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
363
365{
366 clearAddressing();
367}
368
369
370// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
371
372Foam::label Foam::faceZone::whichFace(const label globalFaceID) const
373{
374 return zone::localID(globalFaceID);
375}
376
377
379{
380 if (!patchPtr_)
381 {
382 calcFaceZonePatch();
383 }
384
385 return *patchPtr_;
386}
387
388
390{
391 if (!masterCellsPtr_)
392 {
393 calcCellLayers();
394 }
395
396 return *masterCellsPtr_;
397}
398
399
401{
402 if (!slaveCellsPtr_)
403 {
404 calcCellLayers();
405 }
406
407 return *slaveCellsPtr_;
408}
409
410
412{
413 if (!mePtr_)
414 {
415 mePtr_ =
416 new labelList
417 (
418 operator()().meshEdges
419 (
420 zoneMesh().mesh().edges(),
421 zoneMesh().mesh().pointEdges()
422 )
423 );
424 }
425
426 return *mePtr_;
427}
428
429
431{
433
434 deleteDemandDrivenData(patchPtr_);
435
436 deleteDemandDrivenData(masterCellsPtr_);
437 deleteDemandDrivenData(slaveCellsPtr_);
438
440}
441
442
444(
445 const labelUList& addr,
446 const bool flipMapValue
447)
448{
449 clearAddressing();
451 setFlipMap(flipMapValue);
452}
453
454
456(
457 const labelUList& addr,
458 const boolUList& flipMap
459)
460{
461 clearAddressing();
463 flipMap_ = flipMap;
464}
465
466
468(
469 labelList&& addr,
470 const bool flipMapValue
471)
472{
473 clearAddressing();
475 setFlipMap(flipMapValue);
476}
477
478
480{
481 clearAddressing();
482
483 labelList newAddressing(size());
484 boolList newFlipMap(flipMap_.size());
485 label nFaces = 0;
486
487 const labelList& addr = *this;
488 const labelList& faceMap = mpm.reverseFaceMap();
489
490 forAll(addr, i)
491 {
492 const label facei = addr[i];
493
494 if (faceMap[facei] >= 0)
495 {
496 newAddressing[nFaces] = faceMap[facei];
497 newFlipMap[nFaces] = flipMap_[i]; // Keep flip map.
498 nFaces++;
499 }
500 }
501
502 newAddressing.setSize(nFaces);
503 newFlipMap.setSize(nFaces);
504
505 transfer(newAddressing);
506 flipMap_.transfer(newFlipMap);
507}
508
509
510bool Foam::faceZone::checkDefinition(const bool report) const
511{
512 return zone::checkDefinition(zoneMesh().mesh().faces().size(), report);
513}
514
515
516bool Foam::faceZone::checkParallelSync(const bool report) const
517{
518 const polyMesh& mesh = zoneMesh().mesh();
519 const polyBoundaryMesh& bm = mesh.boundaryMesh();
520
521 bool hasError = false;
522
523
524 // Check that zone faces are synced
525 // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
526
527 {
528 const labelList& addr = *this;
529
530 boolList neiZoneFace(mesh.nBoundaryFaces(), false);
531 boolList neiZoneFlip(mesh.nBoundaryFaces(), false);
532
533 forAll(addr, i)
534 {
535 const label facei = addr[i];
536
537 if (!mesh.isInternalFace(facei))
538 {
539 neiZoneFace[facei-mesh.nInternalFaces()] = true;
540 neiZoneFlip[facei-mesh.nInternalFaces()] = flipMap()[i];
541 }
542 }
543 boolList myZoneFace(neiZoneFace);
545 boolList myZoneFlip(neiZoneFlip);
547
548 forAll(addr, i)
549 {
550 const label facei = addr[i];
551 const label patchi = bm.whichPatch(facei);
552
553 if (patchi != -1 && bm[patchi].coupled())
554 {
555 const label bFacei = facei-mesh.nInternalFaces();
556
557 // Check face in zone on both sides
558 if (myZoneFace[bFacei] != neiZoneFace[bFacei])
559 {
560 hasError = true;
561
562 if (report)
563 {
564 Pout<< " ***Problem with faceZone " << index()
565 << " named " << name()
566 << ". Face " << facei
567 << " on coupled patch "
568 << bm[patchi].name()
569 << " is not consistent with its coupled neighbour."
570 << endl;
571 }
572 else
573 {
574 // w/o report - can stop checking now
575 break;
576 }
577 }
578 else if (myZoneFlip[bFacei] == neiZoneFlip[bFacei])
579 {
580 // Flip state should be opposite.
581 hasError = true;
582
583 if (report)
584 {
585 Pout<< " ***Problem with faceZone " << index()
586 << " named " << name()
587 << ". Face " << facei
588 << " on coupled patch "
589 << bm[patchi].name()
590 << " does not have consistent flipMap"
591 << " across coupled faces."
592 << endl;
593 }
594 else
595 {
596 // w/o report - can stop checking now
597 break;
598 }
599 }
600 }
601 }
602 }
603
604 return returnReduce(hasError, orOp<bool>());
605}
606
607
609{
610 if (patchPtr_)
611 {
612 patchPtr_->movePoints(pts);
613 }
614}
615
617{
618 os << nl << name()
619 << nl << static_cast<const labelList&>(*this)
620 << nl << flipMap();
621}
622
623
625{
626 os.beginBlock(name());
627
628 os.writeEntry("type", type());
630 writeEntry(this->labelsName, os);
631 flipMap().writeEntry("flipMap", os);
632
633 os.endBlock();
634}
635
636
637// * * * * * * * * * * * * * * * Ostream Operator * * * * * * * * * * * * * //
638
640{
641 zn.write(os);
643 return os;
644}
645
646
647// ************************************************************************* //
Macros for easy insertion into run-time selection tables.
#define addToRunTimeSelectionTable(baseType, thisType, argNames)
Add to construction table with typeName as the key.
const word & name() const noexcept
Return the object name.
Definition: IOobjectI.H:65
virtual bool check(const char *operation) const
Check IOstream status for given operation.
Definition: IOstream.C:58
void setSize(const label n)
Alias for resize()
Definition: List.H:218
void operator=(const UList< label > &a)
Assignment to UList operator. Takes linear time.
Definition: List.C:480
void resize(const label len)
Adjust allocated size of list.
Definition: ListI.H:139
void clear()
Clear the list, i.e. set size to zero.
Definition: ListI.H:116
An Ostream is an abstract base class for all output systems (streams, files, token lists,...
Definition: Ostream.H:62
virtual Ostream & endBlock()
Write end block group.
Definition: Ostream.C:105
Ostream & writeEntry(const keyType &key, const T &value)
Write a keyword/value entry.
Definition: Ostream.H:239
virtual Ostream & beginBlock(const keyType &kw)
Write begin block group with the given name.
Definition: Ostream.C:87
A list of faces which address into the list of points.
label size() const noexcept
The number of elements in the UList.
Definition: UListI.H:420
void size(const label n)
Older name for setAddressableSize.
Definition: UList.H:114
A list of keyword definitions, which are a keyword followed by a number of values (eg,...
Definition: dictionary.H:126
A subset of mesh faces organised as a primitive patch.
Definition: faceZone.H:67
virtual bool checkDefinition(const bool report=false) const
Check zone definition. Return true if in error.
Definition: faceZone.C:510
virtual void resetAddressing(const labelUList &addr, const bool flipMapValue)
Reset addressing - use uniform flip map value.
Definition: faceZone.C:444
label whichFace(const label globalCellID) const
Helper function to re-direct to zone::localID(...)
Definition: faceZone.C:372
const labelList & masterCells() const
Definition: faceZone.C:389
const primitiveFacePatch & operator()() const
Return reference to primitive patch.
Definition: faceZone.C:378
virtual void write(Ostream &os) const
Write.
Definition: faceZone.C:616
static const char *const labelsName
Definition: faceZone.H:118
virtual void clearAddressing()
Clear addressing.
Definition: faceZone.C:430
virtual ~faceZone()
Destructor.
Definition: faceZone.C:364
virtual bool checkParallelSync(const bool report=false) const
Check whether all procs have faces synchronised.
Definition: faceZone.C:516
const labelList & slaveCells() const
Return labels of slave cells.
Definition: faceZone.C:400
const labelList & meshEdges() const
Return global edge index for local edges.
Definition: faceZone.C:411
virtual bool write()
Write the output fields.
Foam::dictionary writeDict() const
Write to dictionary.
Class containing mesh-to-mesh mapping information after a change in polyMesh topology.
Definition: mapPolyMesh.H:162
const labelList & reverseFaceMap() const
Reverse face map.
Definition: mapPolyMesh.H:501
void movePoints()
Update for new mesh geometry.
void updateMesh()
Update for new mesh topology.
A polyBoundaryMesh is a polyPatch list with additional search methods and registered IO.
label whichPatch(const label faceIndex) const
Return patch index for a given face label.
Mesh consisting of general polyhedral cells.
Definition: polyMesh.H:81
const polyBoundaryMesh & boundaryMesh() const
Return boundary mesh.
Definition: polyMesh.H:456
bool isInternalFace(const label faceIndex) const noexcept
Return true if given face label is internal to the mesh.
label nBoundaryFaces() const noexcept
Number of boundary faces (== nFaces - nInternalFaces)
label nInternalFaces() const noexcept
Number of internal faces.
Lookup type of boundary radiation properties.
Definition: lookup.H:66
static void swapBoundaryFaceList(const polyMesh &mesh, UList< T > &faceValues)
Swap coupled boundary face values. Uses eqOp.
Definition: syncTools.H:445
A class for handling words, derived from Foam::string.
Definition: word.H:68
Base class for mesh zones.
Definition: zone.H:67
label localID(const label globalID) const
Lookup local address in zone for given global index.
Definition: zone.C:154
virtual void clearAddressing()
Clear addressing.
Definition: zone.C:160
#define defineTypeNameAndDebug(Type, DebugSwitch)
Define the typeName and debug information.
Definition: className.H:121
bool coupled(solutionDict.getOrDefault("coupledEnergyField", false))
dynamicFvMesh & mesh
Template functions to aid in the implementation of demand driven data.
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
Definition: error.H:453
OBJstream os(runTime.globalPath()/outputName)
Foam::faceZoneMesh.
const labelList nFaces(UPstream::listGatherValues< label >(aMesh.nFaces()))
const pointField & points
#define DebugInfo
Report an information message using Foam::Info.
#define WarningInFunction
Report a warning using Foam::Warning.
#define FUNCTION_NAME
#define DebugInFunction
Report an information message using Foam::Info.
const std::string patch
OpenFOAM patch number as a std::string.
Namespace for OpenFOAM.
Pair< int > faceMap(const label facePi, const face &faceP, const label faceNi, const face &faceN)
List< label > labelList
A List of labels.
Definition: List.H:66
fileName::Type type(const fileName &name, const bool followLink=true)
Return the file type: DIRECTORY or FILE, normally following symbolic links.
Definition: MSwindows.C:598
Ostream & operator<<(Ostream &, const boundaryPatch &p)
Write boundaryPatch as dictionary entries (without surrounding braces)
Definition: boundaryPatch.C:83
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:372
errorManip< error > abort(error &err)
Definition: errorManip.H:144
List< bool > boolList
A List of bools.
Definition: List.H:64
PrimitivePatch< List< face >, const pointField & > primitiveFacePatch
A PrimitivePatch with List storage for the faces, const reference for the point field.
error FatalError
word name(const expressions::valueTypeCode typeCode)
A word representation of a valueTypeCode. Empty for INVALID.
Definition: exprTraits.C:59
T returnReduce(const T &value, const BinaryOp &bop, const int tag=UPstream::msgType(), const label comm=UPstream::worldComm)
Reduce (copy) and return value.
prefixOSstream Pout
OSstream wrapped stdout (std::cout) with parallel prefix.
List< face > faceList
A List of faces.
Definition: faceListFwd.H:47
void deleteDemandDrivenData(DataPtr &dataPtr)
constexpr char nl
The newline '\n' character (0x0a)
Definition: Ostream.H:53
labelList f(nPoints)
#define defineRunTimeSelectionTable(baseType, argNames)
Define run-time selection table.
dictionary dict
#define forAll(list, i)
Loop across all elements in list.
Definition: stdFoam.H:333