topoSet.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) 2016-2022 OpenCFD Ltd.
10 -------------------------------------------------------------------------------
11 License
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 "topoSet.H"
30 #include "mapPolyMesh.H"
31 #include "polyMesh.H"
32 #include "boundBox.H"
33 #include "Time.H"
34 
35 // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
36 
37 namespace Foam
38 {
39  defineTypeNameAndDebug(topoSet, 0);
40  defineRunTimeSelectionTable(topoSet, word);
41  defineRunTimeSelectionTable(topoSet, size);
42  defineRunTimeSelectionTable(topoSet, set);
43 
45  (
46  debug::debugSwitch("disallowGenericSets", 0)
47  );
48 }
49 
50 
51 // * * * * * * * * * * * * * * * * Selectors * * * * * * * * * * * * * * * * //
52 
55 (
56  const word& setType,
57  const polyMesh& mesh,
58  const word& name,
61 )
62 {
63  auto* ctorPtr = wordConstructorTable(setType);
64 
65  if (!ctorPtr)
66  {
68  (
69  "set",
70  setType,
71  *wordConstructorTablePtr_
72  ) << exit(FatalError);
73  }
74 
75  return autoPtr<topoSet>(ctorPtr(mesh, name, rOpt, wOpt));
76 }
77 
78 
81 (
82  const word& setType,
83  const polyMesh& mesh,
84  const word& name,
85  const label size,
87 )
88 {
89  auto* ctorPtr = sizeConstructorTable(setType);
90 
91  if (!ctorPtr)
92  {
94  (
95  "set",
96  setType,
97  *sizeConstructorTablePtr_
98  ) << exit(FatalError);
99  }
101  return autoPtr<topoSet>(ctorPtr(mesh, name, size, wOpt));
102 }
103 
104 
107 (
108  const word& setType,
109  const polyMesh& mesh,
110  const word& name,
111  const topoSet& set,
113 )
114 {
115  auto* ctorPtr = setConstructorTable(setType);
116 
117  if (!ctorPtr)
118  {
120  (
121  "set",
122  setType,
123  *setConstructorTablePtr_
124  ) << exit(FatalError);
125  }
126 
127  return autoPtr<topoSet>(ctorPtr(mesh, name, set, wOpt));
128 }
129 
130 
131 // * * * * * * * * * * * * * Static Member Functions * * * * * * * * * * * * //
132 
134 (
135  const polyMesh& mesh,
136  const word& name
137 )
138 {
139  return mesh.facesInstance()/mesh.meshDir()/"sets"/name;
140 }
141 
142 
143 // * * * * * * * * * * * * Protected Member Functions * * * * * * * * * * * //
144 
145 // Update stored cell numbers using map.
146 // Do in two passes to prevent allocation if nothing changed.
148 {
149  labelHashSet& labels = *this;
150 
151  // Iterate over map to see if anything changed
152 
153  bool changed = false;
154 
155  for (const label oldId : labels)
156  {
157  if (oldId < 0 || oldId >= map.size())
158  {
160  << "Illegal content " << oldId << " of set:" << name()
161  << " of type " << type() << nl
162  << "Value should be between [0," << map.size() << ')'
163  << endl
164  << abort(FatalError);
165  }
166 
167  const label newId = map[oldId];
168 
169  if (newId != oldId)
170  {
171  changed = true;
172  #ifdef FULLDEBUG
173  continue; // Check all elements in FULLDEBUG mode
174  #endif
175  break;
176  }
177  }
178 
179  if (!changed)
180  {
181  return;
182  }
183 
184 
185  // Relabel. Use second labelHashSet to prevent overlapping.
186 
187  labelHashSet newLabels(2*labels.size());
188 
189  for (const label oldId : labels)
190  {
191  const label newId = map[oldId];
192 
193  if (newId >= 0)
194  {
195  newLabels.set(newId);
196  }
197  }
198 
199  labels.transfer(newLabels);
200 }
201 
202 
203 void Foam::topoSet::check(const label maxSize)
204 {
205  const labelHashSet& labels = *this;
206 
207  for (const label oldId : labels)
208  {
209  if (oldId < 0 || oldId >= maxSize)
210  {
212  << "Illegal content " << oldId << " of set:" << name()
213  << " of type " << type() << nl
214  << "Value should be between [0," << maxSize << ')'
215  << endl
216  << abort(FatalError);
217  }
218  }
219 }
220 
221 
222 // Write maxElem elements, starting at iter. Updates iter and elemI.
224 (
225  Ostream& os,
226  const label maxElem,
228  label& elemI
229 ) const
230 {
231  label n = 0;
232 
233  for (; (iter != cend()) && (n < maxElem); ++iter)
234  {
235  if (n && ((n % 10) == 0))
236  {
237  os << nl;
238  }
239  os << iter.key() << ' ';
240 
241  ++n;
242  ++elemI;
243  }
244 }
245 
246 
247 // Write maxElem elements, starting at iter. Updates iter and elemI.
249 (
250  Ostream& os,
251  const pointField& coords,
252  const label maxElem,
254  label& elemI
255 ) const
256 {
257  label n = 0;
258 
259  for (; (iter != cend()) && (n < maxElem); ++iter)
260  {
261  if (n && ((n % 3) == 0))
262  {
263  os << nl;
264  }
265  os << iter.key() << coords[iter.key()] << ' ';
266 
267  ++n;
268  ++elemI;
269  }
270 }
271 
272 
274 (
275  Ostream& os,
276  const pointField& coords,
277  const label maxLen
278 ) const
279 {
280  // Bounding box of contents.
281  boundBox bb(pointField(coords, toc()), true);
282 
283  os << "Set bounding box: min = "
284  << bb.min() << " max = " << bb.max() << " metres." << nl << endl;
285 
286  label n = 0;
287 
288  topoSet::const_iterator iter = this->cbegin();
289 
290  if (size() <= maxLen)
291  {
292  writeDebug(os, coords, maxLen, iter, n);
293  }
294  else
295  {
296  label halfLen = maxLen/2;
297 
298  os << "Size larger than " << maxLen << ". Printing first and last "
299  << halfLen << " elements:" << nl << endl;
300 
301  writeDebug(os, coords, halfLen, iter, n);
302 
303  os << nl << " .." << nl << endl;
304 
305  for (; n < size() - halfLen; ++n)
306  {
307  ++iter;
308  }
309 
310  writeDebug(os, coords, halfLen, iter, n);
311  }
312 }
313 
314 
315 // * * * * * * * * * * * * * Static Member Functions * * * * * * * * * * * * //
316 
318 (
319  const polyMesh& mesh,
320  const word& name,
323 )
324 {
325  IOobject io
326  (
327  name,
329  (
330  mesh.meshDir()/"sets",
331  word::null,
334  ),
335  polyMesh::meshSubDir/"sets",
336  mesh,
337  rOpt,
338  wOpt
339  );
340 
341  if (!io.typeHeaderOk<topoSet>(false) && disallowGenericSets != 0)
342  {
343  DebugInfo<< "Setting no read for set " << name << endl;
345  }
346 
347  return io;
348 }
349 
350 
352 (
353  const Time& runTime,
354  const word& name,
357 )
358 {
359  return IOobject
360  (
361  name,
363  (
364  polyMesh::meshSubDir/"sets",
365  word::null,
368  (
370  "faces",
372  )
373  ),
374  polyMesh::meshSubDir/"sets",
375  runTime,
376  rOpt,
377  wOpt
378  );
379 }
380 
381 
382 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
383 
384 Foam::topoSet::topoSet(const IOobject& io, const word& wantedType)
385 :
386  regIOobject(io)
387 {
388  if (isReadRequired() || (isReadOptional() && headerOk()))
389  {
390  if (readStream(wantedType).good())
391  {
392  readStream(wantedType) >> static_cast<labelHashSet&>(*this);
393 
394  close();
395  }
396  }
397 }
398 
399 
401 (
402  const polyMesh& mesh,
403  const word& wantedType,
404  const word& name,
407 )
408 :
409  regIOobject(findIOobject(mesh, name, rOpt, wOpt))
410 {
411  if (isReadRequired() || (isReadOptional() && headerOk()))
412  {
413  if (readStream(wantedType).good())
414  {
415  readStream(wantedType) >> static_cast<labelHashSet&>(*this);
416 
417  close();
418  }
419  }
420 }
421 
422 
424 (
425  const polyMesh& mesh,
426  const word& name,
427  const label size,
429 )
430 :
431  regIOobject(findIOobject(mesh, name, IOobject::NO_READ, wOpt)),
432  labelHashSet(size)
433 {}
434 
435 
437 (
438  const polyMesh& mesh,
439  const word& name,
440  const labelHashSet& labels,
442 )
443 :
444  regIOobject(findIOobject(mesh, name, IOobject::NO_READ, wOpt)),
445  labelHashSet(labels)
446 {}
447 
448 
450 (
451  const polyMesh& mesh,
452  const word& name,
453  labelHashSet&& labels,
455 )
456 :
457  regIOobject(findIOobject(mesh, name, IOobject::NO_READ, wOpt)),
458  labelHashSet(std::move(labels))
459 {}
460 
461 
463 (
464  const polyMesh& mesh,
465  const word& name,
466  const labelUList& labels,
468 )
469 :
470  regIOobject(findIOobject(mesh, name, IOobject::NO_READ, wOpt)),
471  labelHashSet(labels)
472 {}
473 
474 
475 Foam::topoSet::topoSet(const IOobject& io, const label size)
476 :
477  regIOobject(io),
478  labelHashSet(size)
479 {}
480 
481 
483 :
484  regIOobject(io),
485  labelHashSet(labels)
486 {}
487 
488 
490 :
492  labelHashSet(std::move(labels))
493 {}
494 
495 
496 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
498 bool Foam::topoSet::found(const label id) const
499 {
500  return static_cast<const labelHashSet&>(*this).found(id);
501 }
502 
504 bool Foam::topoSet::set(const label id)
505 {
506  return static_cast<labelHashSet&>(*this).set(id);
507 }
508 
510 bool Foam::topoSet::unset(const label id)
511 {
512  return static_cast<labelHashSet&>(*this).unset(id);
513 }
514 
516 void Foam::topoSet::set(const labelUList& labels)
517 {
518  static_cast<labelHashSet&>(*this).set(labels);
519 }
520 
522 void Foam::topoSet::unset(const labelUList& labels)
523 {
524  static_cast<labelHashSet&>(*this).unset(labels);
525 }
526 
527 
528 void Foam::topoSet::invert(const label maxLen)
529 {
530  // Retain a copy of the original (current) set.
531  labelHashSet original
532  (
533  std::move(static_cast<labelHashSet&>(*this))
534  );
535 
536  clear(); // Maybe don't trust the previous move operation
537  reserve(max(64, (maxLen - original.size())));
538 
539  for (label id=0; id < maxLen; ++id)
540  {
541  if (!original.found(id))
542  {
543  this->set(id);
544  }
545  }
546 }
547 
548 
550 {
551  // Only retain entries found in both sets
552  static_cast<labelHashSet&>(*this) &= set;
553 }
554 
555 
557 {
558  // Add entries to the set
559  static_cast<labelHashSet&>(*this) |= set;
560 }
561 
562 
564 {
565  // Subtract entries from the set
566  static_cast<labelHashSet&>(*this) -= set;
567 }
568 
570 void Foam::topoSet::deleteSet(const topoSet& set)
571 {
572  this->subtractSet(set);
573 }
574 
576 void Foam::topoSet::sync(const polyMesh&)
577 {
579 }
580 
581 
582 void Foam::topoSet::writeDebug(Ostream& os, const label maxLen) const
583 {
584  label n = 0;
585 
586  topoSet::const_iterator iter = this->cbegin();
587 
588  if (size() <= maxLen)
589  {
590  writeDebug(os, maxLen, iter, n);
591  }
592  else
593  {
594  label halfLen = maxLen/2;
595 
596  os << "Size larger than " << maxLen << ". Printing first and last "
597  << halfLen << " elements:" << nl << endl;
598 
599  writeDebug(os, halfLen, iter, n);
600 
601  os << nl << " .." << nl << endl;
602 
603  for (; n < size() - halfLen; ++n)
604  {
605  ++iter;
606  }
607 
608  writeDebug(os, halfLen, iter, n);
609  }
610 }
611 
614 {
615  return (os << *this).good();
616 }
617 
620 {
622 }
623 
624 
626 {
627  IOobject io
628  (
629  "dummy",
631  polyMesh::meshSubDir/"sets",
632  mesh
633  );
634  fileName setsDir(io.path());
635 
636  if (debug) DebugVar(setsDir);
637 
638  if (isDir(setsDir))
639  {
640  rmDir(setsDir);
641  }
642 }
643 
644 
645 // * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * //
646 
647 void Foam::topoSet::operator=(const topoSet& rhs)
648 {
650 }
651 
652 
653 // ************************************************************************* //
static IOobject findIOobject(const polyMesh &mesh, const word &name, IOobjectOption::readOption rOpt=IOobjectOption::MUST_READ, IOobjectOption::writeOption wOpt=IOobjectOption::NO_WRITE)
Find IOobject in the polyMesh/sets (used as constructor helper)
Definition: topoSet.C:311
virtual bool writeData(Ostream &) const
Write contents.
Definition: topoSet.C:606
writeOption
Enumeration defining write preferences.
bool set(const Key &key)
Same as insert (no value to overwrite)
Definition: HashSet.H:240
void operator=(const topoSet &)
Copy labelHashSet part only.
Definition: topoSet.C:640
void size(const label n)
Older name for setAddressableSize.
Definition: UList.H:116
A class for handling file names.
Definition: fileName.H:72
readOption readOpt() const noexcept
Get the read option.
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition: errorManip.H:125
const fileName & facesInstance() const
Return the current instance directory for faces.
Definition: polyMesh.C:859
word findInstance(const fileName &dir, const word &name=word::null, IOobjectOption::readOption rOpt=IOobjectOption::MUST_READ, const word &stopInstance=word::null) const
Return time instance (location) of dir that contains the file name (eg, used in reading mesh data)...
Definition: Time.C:725
virtual bool unset(const label id)
Unset an index.
Definition: topoSet.C:503
error FatalError
Error stream (stdout output on all processes), with additional &#39;FOAM FATAL ERROR&#39; header text and sta...
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
Definition: error.H:598
bool found(const Key &key) const
Same as contains()
Definition: HashTable.H:1354
const word & name() const noexcept
Return the object name.
Definition: IOobjectI.H:195
static int disallowGenericSets
Debug switch to disallow the use of generic sets.
Definition: topoSet.H:134
label max(const labelHashSet &set, label maxValue=labelMin)
Find the max value in labelHashSet, optionally limited by second argument.
Definition: hashSets.C:40
constexpr char nl
The newline &#39;\n&#39; character (0x0a)
Definition: Ostream.H:50
int debugSwitch(const char *name, const int deflt=0)
Lookup debug switch or add default value.
Definition: debug.C:222
static word meshSubDir
Return the mesh sub-directory name (usually "polyMesh")
Definition: polyMesh.H:410
engineTime & runTime
virtual bool set(const label id)
Set an index.
Definition: topoSet.C:497
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:531
bool headerOk()
Read and check header info. Does not check the headerClassName.
Definition: regIOobject.C:505
void operator=(const this_type &rhs)
Copy assign.
Definition: HashSet.H:445
bool good() const noexcept
Did last readHeader() succeed?
Definition: IOobjectI.H:298
const Time & time() const
Return the top-level database.
Definition: fvMesh.H:360
#define FatalErrorInLookup(lookupTag, lookupName, lookupTable)
Report an error message using Foam::FatalError.
Definition: error.H:605
bool isReadOptional() const noexcept
True if (LAZY_READ) bits are set [same as READ_IF_PRESENT].
Class containing mesh-to-mesh mapping information after a change in polyMesh topology.
Definition: mapPolyMesh.H:157
fileName path() const
The complete path for the object (with instance, local,...).
Definition: IOobject.C:480
bool isDir(const fileName &name, const bool followLink=true)
Does the name exist as a DIRECTORY in the file system?
Definition: POSIX.C:860
HashSet< label, Hash< label > > labelHashSet
A HashSet of labels, uses label hasher.
Definition: HashSet.H:85
fileName::Type type(const fileName &name, const bool followLink=true)
Return the file type: DIRECTORY or FILE, normally following symbolic links.
Definition: POSIX.C:799
bool unset(const Key &key)
Unset the specified key - same as erase.
Definition: HashSet.H:250
static void removeFiles(const polyMesh &)
Helper: remove all sets files from mesh instance.
Definition: topoSet.C:618
vectorField pointField
pointField is a vectorField.
Definition: pointFieldFwd.H:38
dynamicFvMesh & mesh
virtual void addSet(const topoSet &set)
Add elements present in set.
Definition: topoSet.C:549
word name(const expressions::valueTypeCode typeCode)
A word representation of a valueTypeCode. Empty for expressions::valueTypeCode::INVALID.
Definition: exprTraits.C:127
void close()
Close Istream.
A class for handling words, derived from Foam::string.
Definition: word.H:63
void writeDebug(Ostream &os, const label maxElem, topoSet::const_iterator &iter, label &elemI) const
Write part of contents nicely formatted. Prints labels only.
Definition: topoSet.C:217
topoSet(const topoSet &)=delete
No copy construct.
Reading is optional [identical to LAZY_READ].
static const word null
An empty word.
Definition: word.H:84
virtual void subset(const topoSet &set)
Subset contents. Only elements present in both sets remain.
Definition: topoSet.C:542
patchWriters clear()
virtual void subtractSet(const topoSet &set)
Subtract elements present in set.
Definition: topoSet.C:556
constexpr auto cend(const C &c) -> decltype(c.end())
Return const_iterator to the end of the container c.
Definition: stdFoam.H:223
errorManip< error > abort(error &err)
Definition: errorManip.H:139
bool typeHeaderOk(const bool checkType=true, const bool search=true, const bool verbose=true)
Read header (respects is_globalIOobject trait) and check its info.
bool rmDir(const fileName &directory, const bool silent=false, const bool emptyOnly=false)
Remove a directory and its contents recursively,.
Definition: POSIX.C:1433
#define DebugInfo
Report an information message using Foam::Info.
static autoPtr< topoSet > New(const word &setType, const polyMesh &mesh, const word &name, IOobjectOption::readOption rOpt=IOobjectOption::MUST_READ, IOobjectOption::writeOption wOpt=IOobjectOption::NO_WRITE)
Return a pointer to a toposet read from file.
Definition: topoSet.C:48
An Ostream is an abstract base class for all output systems (streams, files, token lists...
Definition: Ostream.H:56
defineRunTimeSelectionTable(reactionRateFlameArea, dictionary)
int debug
Static debugging option.
virtual void updateLabels(const labelUList &map)
Update map from map.
Definition: topoSet.C:140
OBJstream os(runTime.globalPath()/outputName)
defineTypeNameAndDebug(combustionModel, 0)
constexpr auto cbegin(const C &c) -> decltype(c.begin())
Return const_iterator to the beginning of the container c.
Definition: stdFoam.H:190
bool isReadRequired() const noexcept
True if (MUST_READ | READ_MODIFIED) bits are set.
General set of labels of mesh quantity (points, cells, faces).
Definition: topoSet.H:59
virtual bool found(const label id) const
Has the given index?
Definition: topoSet.C:491
virtual void deleteSet(const topoSet &set)
Deprecated(2018-10) subtract elements present in set.
Definition: topoSet.C:563
fileName meshDir() const
Return the local mesh directory (dbDir()/meshSubDir)
Definition: polyMesh.C:841
Nothing to be read.
triangles reserve(surf.size())
virtual void sync(const polyMesh &mesh)
Sync set across coupled patches.
Definition: topoSet.C:569
regIOobject is an abstract class derived from IOobject to handle automatic object registration with t...
Definition: regIOobject.H:66
virtual void invert(const label maxLen)
Invert contents.
Definition: topoSet.C:521
label n
typename parent_type::const_key_iterator const_iterator
A const_iterator, returning reference to the key.
Definition: HashSet.H:131
Pointer management similar to std::unique_ptr, with some additional methods and type checking...
Definition: HashPtrTable.H:48
#define DebugVar(var)
Report a variable name and value.
Mesh consisting of general polyhedral cells.
Definition: polyMesh.H:74
IOobject io("surfaceFilmProperties", mesh.time().constant(), mesh, IOobject::READ_IF_PRESENT, IOobject::NO_WRITE, IOobject::NO_REGISTER)
virtual void check(const label maxSize)
Check limits on addressable range.
Definition: topoSet.C:196
#define NotImplemented
Issue a FatalErrorIn for a function not currently implemented.
Definition: error.H:686
Defines the attributes of an object for which implicit objectRegistry management is supported...
Definition: IOobject.H:172
virtual void updateMesh(const mapPolyMesh &morphMap)
Update any stored data for new labels. Not implemented.
Definition: topoSet.C:612
List< label > toc(const UList< bool > &bools)
Return the (sorted) values corresponding to &#39;true&#39; entries.
Definition: BitOps.C:158
static fileName localPath(const polyMesh &mesh, const word &name)
Name of file set will use.
Definition: topoSet.C:127
Istream & readStream(const word &, const bool readOnProc=true)
Return Istream and check object type against that given.
Namespace for OpenFOAM.
readOption
Enumeration defining read preferences.