OpenLB 1.8.1
Loading...
Searching...
No Matches
olb::CuboidDecomposition< T, D > Class Template Reference

Decomposition of a physical volume into a set of disjoint cuboids. More...

#include <cuboidDecomposition.h>

+ Inheritance diagram for olb::CuboidDecomposition< T, D >:
+ Collaboration diagram for olb::CuboidDecomposition< T, D >:

Public Member Functions

 CuboidDecomposition (Vector< T, D > origin, T deltaR, Vector< int, D > extent, int nC=1)
 Constructs cuboid decomposition of cuboid with origin and extent.
 
 CuboidDecomposition (const Cuboid< T, D > &motherCuboid, int nC)
 Construction from an given mother cuboid.
 
 CuboidDecomposition (IndicatorF< T, D > &indicatorF, T voxelSize, int nC=1)
 Constructs a cuboid decomposition with uniform spacing of voxelSize which consists of nC cuboids.
 
 CuboidDecomposition (IndicatorF< T, D > &indicatorF, T voxelSize, int nC, std::string minimizeBy)
 Constructs a cuboid decomposition with uniform spacing of voxelSize which consists of nC cuboids shrunken using the minimizeBy strategy.
 
int size () const
 Returns number of cuboids in decomposition.
 
std::optional< int > getC (Vector< T, D > physR, int padding=0) const
 Returns ID of cuboid containing physR within padding.
 
Vector< T, D > getPhysR (LatticeR< D+1 > latticeR) const
 Returns physical position of lattice position.
 
std::optional< LatticeR< D+1 > > getLatticeR (Vector< T, D > physR) const
 Returns lattice position for given physical position if it exists.
 
std::optional< LatticeR< D+1 > > getFloorLatticeR (Vector< T, D > physR) const
 Returns floor lattice position for given physical position if it exists.
 
getDeltaR () const
 Returns spacing between lattice points in physical units.
 
bool isInside (Vector< T, D > physR) const
 Returns true iff physR is covered by the decomposition.
 
const Cuboid< T, D > & get (int iC) const
 Read access to a single cuboid.
 
Cuboid< T, D > & get (int iC)
 Read and write access to a single cuboid.
 
const Cuboid< T, D > & getMotherCuboid () const
 Returns the smallest cuboid that includes all cuboids of the structure.
 
Cuboid< T, D > & getMotherCuboid ()
 Returns the smallest cuboid that includes all cuboids of the structure.
 
void setPeriodicity (Vector< bool, D > periodicity)
 Set flag to enable/disable periodicity depending of direction. Be aware that not all directions are true to ensure boundary conditions like for velocity are not disturbed.
 
std::vector< Cuboid< T, D > > & cuboids ()
 
std::set< int > getNeighborhood (int iCglob, int overlap=0) const
 Returns set of neighbors to cuboid iCglob within overlap.
 
void setWeights (IndicatorF< T, D > &indicatorF)
 Sets the number of full cells of each cuboid.
 
void split (int iC, int p)
 Splits cuboid iC, removes it and adds p cuboids of same volume.
 
void splitRegular (int iC, int width)
 Splits cuboid iC, removes it, adds approx. width^3 sized new cuboids.
 
void splitByWeight (int iC, int p, IndicatorF< T, D > &indicatorF)
 Splits cuboid iC, removes it and adds p cuboids of same weight.
 
void splitFractional (int iC, int iD, std::vector< T > fractions)
 Splits cuboid iC along dimension iD into cuboids of fractions.
 
void remove (int iC)
 Removes the cuboid iC.
 
void remove (IndicatorF< T, D > &indicatorF)
 Removes all cuboids where indicatorF = 0.
 
void removeByWeight ()
 Removes all cuboids where weight = 0.
 
void shrink (int iC, IndicatorF< T, D > &indicatorF)
 Shrink cuboid iC so that no empty planes are left.
 
void shrink (IndicatorF< T, D > &indicatorF)
 Shrink all cuboids so that no empty planes are left.
 
void refine (int factor)
 Refines mesh by splitting each cell into factor^3 cells.
 
bool tryRefineTo (T deltaR)
 Tries to refine mesh to given deltaR.
 
void print () const
 Prints cuboid geometry details.
 
void printExtended ()
 Prints cuboid geometry details plus details of all cuboids.
 
void writeToExistingFile (std::string completeFileName, LoadBalancer< T > &loadBalancer)
 Save CuboidDecomposition into an existing XML File.
 
void writeToFile (std::string fileName, LoadBalancer< T > &loadBalancer)
 Save CuboidDecomposition into XML File.
 
getMinRatio () const
 Returns the minimum of the ratio nX/nY/nZ in the structure.
 
getMaxRatio () const
 Returns the maximum of the ratio nX/nY/nZ in the structure.
 
Vector< T, D > getMinPhysR () const
 Returns the minimum coordinate in the structure.
 
Vector< T, D > getMaxPhysR () const
 Returns the maximum coordinate in the structure.
 
getMinPhysVolume () const
 Returns the minimum volume in the structure.
 
getMaxPhysVolume () const
 Returns the maximum volume in the structure.
 
std::size_t getMinLatticeVolume () const
 Returns the minimum number of nodes in the structure.
 
std::size_t getMaxLatticeVolume () const
 Returns the maximum number of nodes in the structure.
 
std::size_t getMinLatticeWeight () const
 Returns the minimum number of nodes in the structure inside the indicator.
 
std::size_t getMaxLatticeWeight () const
 Returns the maximum number of nodes in the structure inside the indicator.
 
std::size_t getNumNodes () const
 Returns the total number cells (without overlap)
 

Detailed Description

template<typename T, unsigned D>
class olb::CuboidDecomposition< T, D >

Decomposition of a physical volume into a set of disjoint cuboids.

The union of all cuboids is a superset of the decomposed volume. Cuboids are dimensioned s.t. they exactly represent a regular lattice with fixed spacing. Two cuboids are neighbors if the distance between them is less than the lattice spacing.

Definition at line 32 of file cuboidDecompositionMinimizer.h.

Constructor & Destructor Documentation

◆ CuboidDecomposition() [1/4]

template<typename T , unsigned D>
olb::CuboidDecomposition< T, D >::CuboidDecomposition ( Vector< T, D > origin,
T deltaR,
Vector< int, D > extent,
int nC = 1 )

Constructs cuboid decomposition of cuboid with origin and extent.

Definition at line 43 of file cuboidDecomposition.hh.

44 : _motherCuboid(origin, deltaR, extent)
45 , _cuboids{_motherCuboid}
46 , _periodicityOn{}
47{
48 split(0, nC);
49}
void split(int iC, int p)
Splits cuboid iC, removes it and adds p cuboids of same volume.

References olb::CuboidDecomposition< T, D >::split().

+ Here is the call graph for this function:

◆ CuboidDecomposition() [2/4]

template<typename T , unsigned D>
olb::CuboidDecomposition< T, D >::CuboidDecomposition ( const Cuboid< T, D > & motherCuboid,
int nC )

Construction from an given mother cuboid.

Definition at line 52 of file cuboidDecomposition.hh.

53 : CuboidDecomposition(motherCuboid.getOrigin(), motherCuboid.getDeltaR(), motherCuboid.getExtent(), nC)
54{ }
CuboidDecomposition(Vector< T, D > origin, T deltaR, Vector< int, D > extent, int nC=1)
Constructs cuboid decomposition of cuboid with origin and extent.

◆ CuboidDecomposition() [3/4]

template<typename T , unsigned D>
olb::CuboidDecomposition< T, D >::CuboidDecomposition ( IndicatorF< T, D > & indicatorF,
T voxelSize,
int nC = 1 )

Constructs a cuboid decomposition with uniform spacing of voxelSize which consists of nC cuboids.

Definition at line 57 of file cuboidDecomposition.hh.

58 : _motherCuboid(indicatorF.getMin(),
59 voxelSize,
60 (indicatorF.getMax() - indicatorF.getMin()) / voxelSize + 1.5)
61 , _cuboids{_motherCuboid}
62 , _periodicityOn{}
63{
64 _cuboids.reserve(nC+2);
65 if (nC > 1) {
66 split(0, nC);
67 }
68 shrink(indicatorF);
69}
void shrink(int iC, IndicatorF< T, D > &indicatorF)
Shrink cuboid iC so that no empty planes are left.

◆ CuboidDecomposition() [4/4]

template<typename T , unsigned D>
olb::CuboidDecomposition< T, D >::CuboidDecomposition ( IndicatorF< T, D > & indicatorF,
T voxelSize,
int nC,
std::string minimizeBy )

Constructs a cuboid decomposition with uniform spacing of voxelSize which consists of nC cuboids shrunken using the minimizeBy strategy.

Definition at line 72 of file cuboidDecomposition.hh.

73 : _motherCuboid(indicatorF.getMin(), voxelSize, (indicatorF.getMax() - indicatorF.getMin()) / voxelSize + 1.5)
74 , _cuboids{_motherCuboid}
75 , _periodicityOn{}
76{
77 if ( minimizeBy == "volume" ) {
78 minimizeByVolume(*this, indicatorF, nC);
79 }
80 else if ( minimizeBy == "weight" ) {
81 minimizeByWeight(*this, indicatorF, nC);
82 }
83}
void minimizeByWeight(CuboidDecomposition< T, 3 > &cGeometry, IndicatorF3D< T > &indicatorF, int nC)
void minimizeByVolume(CuboidDecomposition< T, 3 > &cGeometry, IndicatorF3D< T > &indicatorF, int nC)
Splits into nC cuboids by-volume.

Member Function Documentation

◆ cuboids()

template<typename T , unsigned D>
std::vector< Cuboid< T, D > > & olb::CuboidDecomposition< T, D >::cuboids ( )
inline

Definition at line 106 of file cuboidDecomposition.h.

106 {
107 return _cuboids;
108 }
+ Here is the caller graph for this function:

◆ get() [1/2]

template<typename T , unsigned D>
Cuboid< T, D > & olb::CuboidDecomposition< T, D >::get ( int iC)

Read and write access to a single cuboid.

Definition at line 141 of file cuboidDecomposition.hh.

142{
143 return _cuboids[iC];
144}

◆ get() [2/2]

template<typename T , unsigned D>
const Cuboid< T, D > & olb::CuboidDecomposition< T, D >::get ( int iC) const

Read access to a single cuboid.

Definition at line 135 of file cuboidDecomposition.hh.

136{
137 return _cuboids.at(iC);
138}
+ Here is the caller graph for this function:

◆ getC()

template<typename T , unsigned D>
std::optional< int > olb::CuboidDecomposition< T, D >::getC ( Vector< T, D > physR,
int padding = 0 ) const

Returns ID of cuboid containing physR within padding.

Definition at line 92 of file cuboidDecomposition.hh.

92 {
93 for (int iC = 0; iC < size(); ++iC) {
94 if (get(iC).isInside(physR, padding)) {
95 return iC;
96 }
97 }
98 return std::nullopt;
99}
int size() const
Returns number of cuboids in decomposition.
bool isInside(Vector< T, D > physR) const
Returns true iff physR is covered by the decomposition.
const Cuboid< T, D > & get(int iC) const
Read access to a single cuboid.
+ Here is the caller graph for this function:

◆ getDeltaR()

template<typename T , unsigned D>
T olb::CuboidDecomposition< T, D >::getDeltaR ( ) const

Returns spacing between lattice points in physical units.

Definition at line 120 of file cuboidDecomposition.hh.

120 {
121 return _motherCuboid.getDeltaR();
122}
+ Here is the caller graph for this function:

◆ getFloorLatticeR()

template<typename T , unsigned D>
std::optional< LatticeR< D+1 > > olb::CuboidDecomposition< T, D >::getFloorLatticeR ( Vector< T, D > physR) const

Returns floor lattice position for given physical position if it exists.

Definition at line 111 of file cuboidDecomposition.hh.

111 {
112 if (auto iC = getC(physR, 0)) {
113 const auto& c = get(*iC);
114 return LatticeR<D>{util::floor((physR - c.getOrigin()) / c.getDeltaR())}.withPrefix(*iC);
115 }
116 return std::nullopt;
117}
std::optional< int > getC(Vector< T, D > physR, int padding=0) const
Returns ID of cuboid containing physR within padding.
platform_constant int c[Q][D]
Definition functions.h:57
ADf< T, DIM > floor(const ADf< T, DIM > &a)
Definition aDiff.h:869
Vector< std::int32_t, D > LatticeR
Type for spatial block-local lattice coordinates.

◆ getLatticeR()

template<typename T , unsigned D>
std::optional< LatticeR< D+1 > > olb::CuboidDecomposition< T, D >::getLatticeR ( Vector< T, D > physR) const

Returns lattice position for given physical position if it exists.

Definition at line 102 of file cuboidDecomposition.hh.

102 {
103 if (auto iC = getC(physR, 0)) {
104 const auto& c = get(*iC);
105 return LatticeR<D>{util::floor((physR - c.getOrigin()) / c.getDeltaR() + 0.5)}.withPrefix(*iC);
106 }
107 return std::nullopt;
108}
+ Here is the caller graph for this function:

◆ getMaxLatticeVolume()

template<typename T , unsigned D>
std::size_t olb::CuboidDecomposition< T, D >::getMaxLatticeVolume ( ) const

Returns the maximum number of nodes in the structure.

Definition at line 509 of file cuboidDecomposition.hh.

510{
511 std::size_t maxNodes = _cuboids[0].getLatticeVolume();
512 for (unsigned i = 0; i < _cuboids.size(); i++) {
513 if (_cuboids[i].getLatticeVolume() > maxNodes) {
514 maxNodes = _cuboids[i].getLatticeVolume();
515 }
516 }
517 return maxNodes;
518}

◆ getMaxLatticeWeight()

template<typename T , unsigned D>
std::size_t olb::CuboidDecomposition< T, D >::getMaxLatticeWeight ( ) const

Returns the maximum number of nodes in the structure inside the indicator.

Definition at line 543 of file cuboidDecomposition.hh.

544{
545 std::size_t maxNodes = _cuboids[0].getWeight();
546 for (unsigned i = 0; i < _cuboids.size(); i++) {
547 if (_cuboids[i].getWeight() > maxNodes) {
548 maxNodes = _cuboids[i].getWeight();
549 }
550 }
551 return maxNodes;
552}

◆ getMaxPhysR()

template<typename T , unsigned D>
Vector< T, D > olb::CuboidDecomposition< T, D >::getMaxPhysR ( ) const

Returns the maximum coordinate in the structure.

Definition at line 456 of file cuboidDecomposition.hh.

457{
458 Vector<T,D> output(_cuboids[0].getOrigin());
459 for (unsigned iD=0; iD < D; ++iD) {
460 output[iD] += _cuboids[0].getExtent()[iD]*_cuboids[0].getDeltaR();
461 }
462 for (unsigned i = 0; i < _cuboids.size(); i++) {
463 for (unsigned iD=0; iD < D; ++iD) {
464 if (_cuboids[i].getOrigin()[iD] + _cuboids[i].getExtent()[iD]*_cuboids[i].getDeltaR() > output[iD]) {
465 output[iD] = _cuboids[i].getOrigin()[iD] + _cuboids[i].getExtent()[iD]*_cuboids[i].getDeltaR();
466 }
467 }
468 }
469 return output;
470}
T getDeltaR() const
Returns spacing between lattice points in physical units.

◆ getMaxPhysVolume()

template<typename T , unsigned D>
T olb::CuboidDecomposition< T, D >::getMaxPhysVolume ( ) const

Returns the maximum volume in the structure.

Definition at line 485 of file cuboidDecomposition.hh.

486{
487 T maxVolume = _cuboids[0].getPhysVolume();
488 for (unsigned i = 0; i < _cuboids.size(); i++) {
489 if (_cuboids[i].getPhysVolume() > maxVolume) {
490 maxVolume = _cuboids[i].getPhysVolume();
491 }
492 }
493 return maxVolume;
494}

◆ getMaxRatio()

template<typename T , unsigned D>
T olb::CuboidDecomposition< T, D >::getMaxRatio ( ) const

Returns the maximum of the ratio nX/nY/nZ in the structure.

Definition at line 422 of file cuboidDecomposition.hh.

423{
424 T maxRatio = 1.;
425 for (unsigned i = 0; i < _cuboids.size(); i++) {
426 if ((T)_cuboids[i].getNx() / (T)_cuboids[i].getNy() > maxRatio) {
427 maxRatio = (T)_cuboids[i].getNx() / (T)_cuboids[i].getNy();
428 }
429 if constexpr (D == 3) {
430 if ((T)_cuboids[i].getNy() / (T)_cuboids[i].getNz() > maxRatio) {
431 maxRatio = (T)_cuboids[i].getNy() / (T)_cuboids[i].getNz();
432 }
433 if ((T)_cuboids[i].getNz() / (T)_cuboids[i].getNx() > maxRatio) {
434 maxRatio = (T)_cuboids[i].getNz() / (T)_cuboids[i].getNx();
435 }
436 }
437 }
438 return maxRatio;
439}

◆ getMinLatticeVolume()

template<typename T , unsigned D>
std::size_t olb::CuboidDecomposition< T, D >::getMinLatticeVolume ( ) const

Returns the minimum number of nodes in the structure.

Definition at line 497 of file cuboidDecomposition.hh.

498{
499 std::size_t minNodes = _cuboids[0].getLatticeVolume();
500 for (unsigned i = 0; i < _cuboids.size(); i++) {
501 if (_cuboids[i].getLatticeVolume() < minNodes) {
502 minNodes = _cuboids[i].getLatticeVolume();
503 }
504 }
505 return minNodes;
506}

◆ getMinLatticeWeight()

template<typename T , unsigned D>
std::size_t olb::CuboidDecomposition< T, D >::getMinLatticeWeight ( ) const

Returns the minimum number of nodes in the structure inside the indicator.

Definition at line 531 of file cuboidDecomposition.hh.

532{
533 std::size_t minNodes = _cuboids[0].getWeight();
534 for (unsigned i = 0; i < _cuboids.size(); i++) {
535 if (_cuboids[i].getWeight() < minNodes) {
536 minNodes = _cuboids[i].getWeight();
537 }
538 }
539 return minNodes;
540}

◆ getMinPhysR()

template<typename T , unsigned D>
Vector< T, D > olb::CuboidDecomposition< T, D >::getMinPhysR ( ) const

Returns the minimum coordinate in the structure.

Definition at line 442 of file cuboidDecomposition.hh.

443{
444 Vector<T,D> output(_cuboids[0].getOrigin());
445 for (int i = 0; i < size(); i++) {
446 for (unsigned iD=0; iD < D; ++iD) {
447 if (_cuboids[i].getOrigin()[iD] < output[iD]) {
448 output[iD] = _cuboids[i].getOrigin()[iD];
449 }
450 }
451 }
452 return output;
453}

◆ getMinPhysVolume()

template<typename T , unsigned D>
T olb::CuboidDecomposition< T, D >::getMinPhysVolume ( ) const

Returns the minimum volume in the structure.

Definition at line 473 of file cuboidDecomposition.hh.

474{
475 T minVolume = _cuboids[0].getPhysVolume();
476 for (unsigned i = 0; i < _cuboids.size(); i++) {
477 if (_cuboids[i].getPhysVolume() < minVolume) {
478 minVolume = _cuboids[i].getPhysVolume();
479 }
480 }
481 return minVolume;
482}

◆ getMinRatio()

template<typename T , unsigned D>
T olb::CuboidDecomposition< T, D >::getMinRatio ( ) const

Returns the minimum of the ratio nX/nY/nZ in the structure.

Definition at line 402 of file cuboidDecomposition.hh.

403{
404 T minRatio = 1.;
405 for (unsigned i = 0; i < _cuboids.size(); i++) {
406 if ((T)_cuboids[i].getNx() / (T)_cuboids[i].getNy() < minRatio) {
407 minRatio = (T)_cuboids[i].getNx() / (T)_cuboids[i].getNy();
408 }
409 if constexpr (D == 3) {
410 if ((T)_cuboids[i].getNy() / (T)_cuboids[i].getNz() < minRatio) {
411 minRatio = (T)_cuboids[i].getNy() / (T)_cuboids[i].getNz();
412 }
413 if ((T)_cuboids[i].getNz() / (T)_cuboids[i].getNx() < minRatio) {
414 minRatio = (T)_cuboids[i].getNz() / (T)_cuboids[i].getNx();
415 }
416 }
417 }
418 return minRatio;
419}

◆ getMotherCuboid() [1/2]

template<typename T , unsigned D>
Cuboid< T, D > & olb::CuboidDecomposition< T, D >::getMotherCuboid ( )

Returns the smallest cuboid that includes all cuboids of the structure.

Definition at line 153 of file cuboidDecomposition.hh.

154{
155 return _motherCuboid;
156}

◆ getMotherCuboid() [2/2]

template<typename T , unsigned D>
const Cuboid< T, D > & olb::CuboidDecomposition< T, D >::getMotherCuboid ( ) const

Returns the smallest cuboid that includes all cuboids of the structure.

Definition at line 147 of file cuboidDecomposition.hh.

148{
149 return _motherCuboid;
150}
+ Here is the caller graph for this function:

◆ getNeighborhood()

template<typename T , unsigned D>
std::set< int > olb::CuboidDecomposition< T, D >::getNeighborhood ( int iCglob,
int overlap = 0 ) const

Returns set of neighbors to cuboid iCglob within overlap.

Definition at line 188 of file cuboidDecomposition.hh.

189{
190 std::set<int> dummy;
191 if constexpr (D == 3) {
192 for (int iC = 0; iC < size(); iC++) {
193 if (cuboid == iC) {
194 continue;
195 }
196 T globX = get(iC).getOrigin()[0];
197 T globY = get(iC).getOrigin()[1];
198 T globZ = get(iC).getOrigin()[2];
199 T nX = get(iC).getNx();
200 T nY = get(iC).getNy();
201 T nZ = get(iC).getNz();
202 T deltaR = get(iC).getDeltaR();
203 if (get(cuboid).intersects({globX - overlap * deltaR,
204 globY - overlap * deltaR,
205 globZ - overlap * deltaR},
206 {globX + (nX + overlap - 1)*deltaR,
207 globY + (nY + overlap - 1)*deltaR,
208 globZ + (nZ + overlap - 1)*deltaR}, overlap)) {
209 dummy.insert(iC);
210 }
211
212 if (_periodicityOn[0]) {
213 if (get(cuboid).getOrigin()[0] + (get(cuboid).getNx() + overlap - 1)*get(cuboid).getDeltaR() > getMaxPhysR()[0]) {
214 Cuboid<T,D> cub({get(cuboid).getOrigin()[0]-getMaxPhysR()[0],
215 get(cuboid).getOrigin()[1],
216 get(cuboid).getOrigin()[2]},
217 get(cuboid).getDeltaR(),
218 {get(cuboid).getNx(),
219 get(cuboid).getNy(),
220 get(cuboid).getNz()});
221 if (cub.intersects({globX - overlap * deltaR,
222 globY - overlap * deltaR,
223 globZ - overlap * deltaR},
224 {globY + (nY + overlap - 1)*deltaR,
225 globX + (nX + overlap - 1)*deltaR,
226 globZ + (nZ + overlap - 1)*deltaR}, overlap)) {
227 dummy.insert(iC);
228 }
229 }
230 if (get(cuboid).getOrigin()[0] - overlap*get(cuboid).getDeltaR() < getMinPhysR()[0]) {
231 Cuboid<T,D> cub({get(cuboid).getOrigin()[0]+getMaxPhysR()[0],
232 get(cuboid).getOrigin()[1],
233 get(cuboid).getOrigin()[2]},
234 get(cuboid).getDeltaR(),
235 {get(cuboid).getNx(),
236 get(cuboid).getNy(),
237 get(cuboid).getNz()});
238 if (cub.intersects({globX - overlap * deltaR,
239 globY - overlap * deltaR,
240 globZ - overlap * deltaR},
241 {globX + (nX + overlap - 1)*deltaR,
242 globY + (nY + overlap - 1)*deltaR,
243 globZ + (nZ + overlap - 1)*deltaR}, overlap)) {
244 dummy.insert(iC);
245 }
246 }
247 }
248
249 if (_periodicityOn[1]) {
250 if (get(cuboid).getOrigin()[1] + (get(cuboid).getNy() + overlap - 1)*get(cuboid).getDeltaR() > getMaxPhysR()[1]) {
251 Cuboid<T,D> cub({get(cuboid).getOrigin()[0],
252 get(cuboid).getOrigin()[1]-getMaxPhysR()[1],
253 get(cuboid).getOrigin()[2]},
254 get(cuboid).getDeltaR(),
255 {get(cuboid).getNx(),
256 get(cuboid).getNy(),
257 get(cuboid).getNz()});
258 if (cub.intersects({globX - overlap * deltaR,
259 globY - overlap * deltaR,
260 globZ - overlap * deltaR},
261 {globX + (nX + overlap - 1)*deltaR,
262 globY + (nY + overlap - 1)*deltaR,
263 globZ + (nZ + overlap - 1)*deltaR}, overlap)) {
264 dummy.insert(iC);
265 }
266 }
267 if (get(cuboid).getOrigin()[1] - overlap*get(cuboid).getDeltaR() < getMinPhysR()[1]) {
268 Cuboid<T,D> cub({get(cuboid).getOrigin()[0],
269 get(cuboid).getOrigin()[1]+getMaxPhysR()[1],
270 get(cuboid).getOrigin()[2]},
271 get(cuboid).getDeltaR(),
272 {get(cuboid).getNx(),
273 get(cuboid).getNy(),
274 get(cuboid).getNz()});
275 if (cub.intersects({globX - overlap * deltaR,
276 globY - overlap * deltaR,
277 globZ - overlap * deltaR},
278 {globX + (nX + overlap - 1)*deltaR,
279 globY + (nY + overlap - 1)*deltaR,
280 globZ + (nZ + overlap - 1)*deltaR}, overlap)) {
281 dummy.insert(iC);
282 }
283 }
284 }
285
286 if (_periodicityOn[2]) {
287 if (get(cuboid).getOrigin()[2] + (get(cuboid).getNz() + overlap - 1)*get(cuboid).getDeltaR() > getMaxPhysR()[2]) {
288 Cuboid<T,D> cub({get(cuboid).getOrigin()[0],
289 get(cuboid).getOrigin()[1],
290 get(cuboid).getOrigin()[2]-getMaxPhysR()[2]},
291 get(cuboid).getDeltaR(),
292 {get(cuboid).getNx(),
293 get(cuboid).getNy(),
294 get(cuboid).getNz()});
295 if (cub.intersects({globX - overlap * deltaR,
296 globY - overlap * deltaR,
297 globZ - overlap * deltaR},
298 {globX + (nX + overlap - 1)*deltaR,
299 globY + (nY + overlap - 1)*deltaR,
300 globZ + (nZ + overlap - 1)*deltaR}, overlap)) {
301 dummy.insert(iC);
302 }
303 }
304 if (get(cuboid).getOrigin()[2] - overlap*get(cuboid).getDeltaR() < getMinPhysR()[2]) {
305 Cuboid<T,D> cub({get(cuboid).getOrigin()[0],
306 get(cuboid).getOrigin()[1],
307 get(cuboid).getOrigin()[2]+getMaxPhysR()[2]},
308 get(cuboid).getDeltaR(),
309 {get(cuboid).getNx(),
310 get(cuboid).getNy(),
311 get(cuboid).getNz()});
312 if (cub.intersects({globX - overlap * deltaR,
313 globY - overlap * deltaR,
314 globZ - overlap * deltaR},
315 {globX + (nX + overlap - 1)*deltaR,
316 globY + (nY + overlap - 1)*deltaR,
317 globZ + (nZ + overlap - 1)*deltaR}, overlap)) {
318 dummy.insert(iC);
319 }
320 }
321 }
322 }
323 } else if constexpr (D == 2) {
324 for (int iC = 0; iC < size(); iC++) {
325 if (cuboid == iC) {
326 continue;
327 }
328 T globX = get(iC).getOrigin()[0];
329 T globY = get(iC).getOrigin()[1];
330 T nX = get(iC).getNx();
331 T nY = get(iC).getNy();
332 T deltaR = get(iC).getDeltaR();
333 if (get(cuboid).intersects({globX,
334 globY - overlap * deltaR},
335 {globX + (nX + overlap - 1)*deltaR,
336 globY + (nY + overlap - 1)*deltaR}, overlap)) {
337 dummy.insert(iC);
338 }
339 if (_periodicityOn[0]) {
340 if (get(cuboid).getOrigin()[0] + (get(cuboid).getNx() + overlap - 1)*get(cuboid).getDeltaR() > getMaxPhysR()[0]) {
341 Cuboid2D<T> cub({get(cuboid).getOrigin()[0]-getMaxPhysR()[0],
342 get(cuboid).getOrigin()[1]},
343 get(cuboid).getDeltaR(),
344 {get(cuboid).getNx(),
345 get(cuboid).getNy()});
346 if (cub.intersects({globX - overlap * deltaR,
347 globY - overlap * deltaR},
348 {globX + (nX + overlap - 1)*deltaR,
349 globY + (nY + overlap - 1)*deltaR}, overlap)) {
350 dummy.insert(iC);
351 }
352 }
353 if (get(cuboid).getOrigin()[0] - overlap*get(cuboid).getDeltaR() < getMinPhysR()[0]) {
354 Cuboid2D<T> cub({get(cuboid).getOrigin()[0]+getMaxPhysR()[0],
355 get(cuboid).getOrigin()[1]},
356 get(cuboid).getDeltaR(),
357 {get(cuboid).getNx(),
358 get(cuboid).getNy()});
359 if (cub.intersects({globX - overlap * deltaR,
360 globY - overlap * deltaR},
361 {globX + (nX + overlap - 1)*deltaR,
362 globY + (nY + overlap - 1)*deltaR}, overlap)) {
363 dummy.insert(iC);
364 }
365 }
366 }
367
368 if (_periodicityOn[1]) {
369 if (get(cuboid).getOrigin()[1] + (get(cuboid).getNy() + overlap - 1)*get(cuboid).getDeltaR() > getMaxPhysR()[1]) {
370 Cuboid2D<T> cub({get(cuboid).getOrigin()[0],
371 get(cuboid).getOrigin()[1]-getMaxPhysR()[1]},
372 get(cuboid).getDeltaR(),
373 {get(cuboid).getNx(),
374 get(cuboid).getNy()});
375 if (cub.intersects({globX - overlap * deltaR,
376 globY - overlap * deltaR},
377 {globX + (nX + overlap - 1)*deltaR,
378 globY + (nY + overlap - 1)*deltaR}, overlap)) {
379 dummy.insert(iC);
380 }
381 }
382 if (get(cuboid).getOrigin()[1] - overlap*get(cuboid).getDeltaR() < getMinPhysR()[1]) {
383 Cuboid2D<T> cub({get(cuboid).getOrigin()[0],
384 get(cuboid).getOrigin()[1]+getMaxPhysR()[1]},
385 get(cuboid).getDeltaR(),
386 {get(cuboid).getNx(),
387 get(cuboid).getNy()});
388 if (cub.intersects({globX - overlap * deltaR,
389 globY - overlap * deltaR},
390 {globX + (nX + overlap - 1)*deltaR,
391 globY + (nY + overlap - 1)*deltaR}, overlap)) {
392 dummy.insert(iC);
393 }
394 }
395 }
396 }
397 }
398 return dummy;
399}
Vector< T, D > getMaxPhysR() const
Returns the maximum coordinate in the structure.
Vector< T, D > getMinPhysR() const
Returns the minimum coordinate in the structure.
Cuboid< T, 2 > Cuboid2D
Definition cuboid.h:149
+ Here is the caller graph for this function:

◆ getNumNodes()

template<typename T , unsigned D>
std::size_t olb::CuboidDecomposition< T, D >::getNumNodes ( ) const

Returns the total number cells (without overlap)

Definition at line 521 of file cuboidDecomposition.hh.

522{
523 std::size_t numNodes = 0;
524 for (unsigned i = 0; i < _cuboids.size(); i++) {
525 numNodes = _cuboids[i].getLatticeVolume();
526 }
527 return numNodes;
528}

◆ getPhysR()

template<typename T , unsigned D>
Vector< T, D > olb::CuboidDecomposition< T, D >::getPhysR ( LatticeR< D+1 > latticeR) const

Returns physical position of lattice position.

Definition at line 159 of file cuboidDecomposition.hh.

160{
161 auto physR = get(latticeR[0]).getPhysR(latticeR.withoutPrefix());
162 for (unsigned iD=0; iD < D; ++iD) {
163 if (_periodicityOn[iD]) {
164 physR[iD] = remainder(physR[iD] - _motherCuboid.getOrigin()[iD]
165 + _motherCuboid.getDeltaR() * (_motherCuboid.getExtent()[iD]),
166 _motherCuboid.getDeltaR() * (_motherCuboid.getExtent()[iD]));
167 // solving the rounding error problem for double
168 if (physR[iD]*physR[iD] < 0.001 * _motherCuboid.getDeltaR()*_motherCuboid.getDeltaR()) {
169 physR[iD] = T{};
170 }
171 // make it to mod instead remainer
172 if (physR[iD] < 0) {
173 physR[iD] += _motherCuboid.getDeltaR() * (_motherCuboid.getExtent()[iD]);
174 }
175 physR[iD] += _motherCuboid.getOrigin()[iD];
176 }
177 }
178 return physR;
179}
+ Here is the caller graph for this function:

◆ isInside()

template<typename T , unsigned D>
bool olb::CuboidDecomposition< T, D >::isInside ( Vector< T, D > physR) const

Returns true iff physR is covered by the decomposition.

Definition at line 125 of file cuboidDecomposition.hh.

125 {
126 for (unsigned i = 0; i < _cuboids.size(); i++) {
127 if (_cuboids[i].isInside(physR, 1)) {
128 return true;
129 }
130 }
131 return false;
132}
+ Here is the caller graph for this function:

◆ print()

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::print ( ) const

Prints cuboid geometry details.

Definition at line 977 of file cuboidDecomposition.hh.

978{
979 OstreamManager clout(std::cout, "CuboidDecomposition");
980 clout << "---Cuboid Structure Statistics---" << std::endl;
981 clout << " Number of Cuboids: " << "\t" << size() << std::endl;
982 clout << " Delta : " << "\t" << "\t" << getDeltaR() << std::endl;
983 clout << " Ratio (min): " << "\t" << "\t" << getMinRatio() << std::endl;
984 clout << " (max): " << "\t" << "\t" << getMaxRatio() << std::endl;
985 clout << " Nodes (min): " << "\t" << "\t" << getMinLatticeVolume() << std::endl;
986 clout << " (max): " << "\t" << "\t" << getMaxLatticeVolume() << std::endl;
987 clout << " Weight (min): " << "\t" << "\t" << getMinLatticeWeight() << std::endl;
988 clout << " (max): " << "\t" << "\t" << getMaxLatticeWeight() << std::endl;
989 clout << "--------------------------------" << std::endl;
990}
std::size_t getMinLatticeVolume() const
Returns the minimum number of nodes in the structure.
std::size_t getMaxLatticeWeight() const
Returns the maximum number of nodes in the structure inside the indicator.
std::size_t getMinLatticeWeight() const
Returns the minimum number of nodes in the structure inside the indicator.
T getMaxRatio() const
Returns the maximum of the ratio nX/nY/nZ in the structure.
std::size_t getMaxLatticeVolume() const
Returns the maximum number of nodes in the structure.
T getMinRatio() const
Returns the minimum of the ratio nX/nY/nZ in the structure.

◆ printExtended()

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::printExtended ( )

Prints cuboid geometry details plus details of all cuboids.

Definition at line 993 of file cuboidDecomposition.hh.

994{
995 OstreamManager clout(std::cout, "CuboidDecomposition");
996 clout << "Mothercuboid :" << std::endl;
997 getMotherCuboid().print();
998
999 for (int iC = 0; iC < size(); iC++) {
1000 clout << "Cuboid #" << iC << ": " << std::endl;
1001 get(iC).print();
1002 }
1003}
const Cuboid< T, D > & getMotherCuboid() const
Returns the smallest cuboid that includes all cuboids of the structure.

◆ refine()

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::refine ( int factor)

Refines mesh by splitting each cell into factor^3 cells.

Definition at line 710 of file cuboidDecomposition.hh.

711{
712 _motherCuboid.refine(factor);
713 for (auto& cuboid : _cuboids) {
714 cuboid.refine(factor);
715 }
716 // Fix neighbor relationships
717 for (int iC=0; iC < size(); ++iC) {
718 auto& iCuboid = get(iC);
719 auto inconsistentNeighbors = getNeighborhood(iC, 2);
720 for (int jC : inconsistentNeighbors) {
721 auto& jCuboid = get(jC);
722 for (unsigned iD=0; iD < D; ++iD) {
723 auto extent = iCuboid.getExtent();
724 if (iCuboid.getOrigin()[iD] + extent[iD]*iCuboid.getDeltaR() < jCuboid.getOrigin()[iD]) {
725 extent[iD] += (jCuboid.getOrigin()[iD] - (iCuboid.getOrigin()[iD] + extent[iD]*iCuboid.getDeltaR())) / iCuboid.getDeltaR() > std::numeric_limits<T>::epsilon();
726 iCuboid.resize(0, extent);
727 }
728 }
729 }
730 }
731}
std::set< int > getNeighborhood(int iCglob, int overlap=0) const
Returns set of neighbors to cuboid iCglob within overlap.

◆ remove() [1/2]

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::remove ( IndicatorF< T, D > & indicatorF)

Removes all cuboids where indicatorF = 0.

Definition at line 561 of file cuboidDecomposition.hh.

562{
563 std::vector<bool> allZero{};
564 LatticeR<D+1> latticeR{};
565 for (int iC = 0; iC < size(); iC++) {
566 latticeR[0] = iC;
567 allZero.push_back(true);
568 for (int iX = 0; iX < _cuboids[iC].getNx(); iX++) {
569 latticeR[1] = iX;
570 for (int iY = 0; iY < _cuboids[iC].getNy(); iY++) {
571 latticeR[2] = iY;
572 if constexpr (D == 3) {
573 for (int iZ = 0; iZ < _cuboids[iC].getNz(); iZ++) {
574 latticeR[3] = iZ;
575 auto physR = getPhysR(latticeR);
576 bool inside[1];
577 indicatorF(inside, physR.data());
578 if (inside[0]) {
579 allZero[iC] = 0;
580 }
581 }
582 } else {
583 auto physR = getPhysR(latticeR);
584 bool inside[1];
585 indicatorF(inside, physR.data());
586 if (inside[0]) {
587 allZero[iC] = 0;
588 }
589 }
590 }
591 }
592 }
593 for (int iC = _cuboids.size() - 1; iC >= 0; iC--) {
594 if (allZero[iC]) {
595 remove(iC);
596 }
597 }
598}
Vector< T, D > getPhysR(LatticeR< D+1 > latticeR) const
Returns physical position of lattice position.
void remove(int iC)
Removes the cuboid iC.

References olb::Vector< T, Size >::data().

+ Here is the call graph for this function:

◆ remove() [2/2]

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::remove ( int iC)

Removes the cuboid iC.

Definition at line 555 of file cuboidDecomposition.hh.

555 {
556 _cuboids.erase(_cuboids.begin() + iC);
557}
+ Here is the caller graph for this function:

◆ removeByWeight()

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::removeByWeight ( )

Removes all cuboids where weight = 0.

Definition at line 601 of file cuboidDecomposition.hh.

602{
603 std::vector<bool> allZero(_cuboids.size(), false);
604 for (unsigned iC = 0; iC < _cuboids.size(); iC++) {
605 allZero[iC] = (_cuboids[iC].getWeight() == 0);
606 }
607 for (int iC = _cuboids.size() - 1; iC >= 0; iC--) {
608 if (allZero[iC]) {
609 remove(iC);
610 }
611 }
612}

◆ setPeriodicity()

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::setPeriodicity ( Vector< bool, D > periodicity)

Set flag to enable/disable periodicity depending of direction. Be aware that not all directions are true to ensure boundary conditions like for velocity are not disturbed.

Definition at line 182 of file cuboidDecomposition.hh.

183{
184 _periodicityOn = periodicity;
185}

◆ setWeights()

template<typename T , unsigned D>
requires (D == 3)
void olb::CuboidDecomposition< T, D >::setWeights ( IndicatorF< T, D > & indicatorF)

Sets the number of full cells of each cuboid.

Definition at line 946 of file cuboidDecomposition.hh.

947{
948 #ifdef PARALLEL_MODE_OMP
949 #pragma omp parallel for schedule(dynamic,1)
950 #endif
951 for (int iC=0; iC < size(); ++iC) {
952 int latticeR[4] { iC, 0, 0, 0 };
953 int xN = get(iC).getNx();
954 int yN = get(iC).getNy();
955 int zN = get(iC).getNz();
956 size_t fullCells = 0;
957 for (int iX = 0; iX < xN; iX++) {
958 for (int iY = 0; iY < yN; iY++) {
959 for (int iZ = 0; iZ < zN; iZ++) {
960 latticeR[1] = iX;
961 latticeR[2] = iY;
962 latticeR[3] = iZ;
963 auto physR = getPhysR(latticeR);
964 bool inside[1];
965 indicatorF(inside,physR.data());
966 if (inside[0]) {
967 fullCells++;
968 }
969 }
970 }
971 }
972 get(iC).setWeight(fullCells);
973 }
974}

References olb::Vector< T, Size >::data().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ shrink() [1/2]

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::shrink ( IndicatorF< T, D > & indicatorF)

Shrink all cuboids so that no empty planes are left.

Definition at line 697 of file cuboidDecomposition.hh.

698{
699 for (int iC = size() - 1; iC >= 0; iC--) {
700 shrink(iC, indicatorF);
701 }
702 // shrink mother cuboid
703 Vector<T,D> minPhysR = getMinPhysR();
704 Vector<T,D> maxPhysR = getMaxPhysR();
705 T deltaR = getDeltaR();
706 _motherCuboid = Cuboid<T,D>(minPhysR, deltaR, (maxPhysR - minPhysR) / deltaR + 0.5);
707}

◆ shrink() [2/2]

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::shrink ( int iC,
IndicatorF< T, D > & indicatorF )

Shrink cuboid iC so that no empty planes are left.

Definition at line 615 of file cuboidDecomposition.hh.

616{
617 if constexpr (D == 3) {
618 LatticeR<D+1> latticeR{};
619 bool inside[1] {};
620
621 latticeR[0] = iC;
622 std::size_t fullCells = 0;
623 int xN = get(iC).getNx();
624 int yN = get(iC).getNy();
625 int zN = get(iC).getNz();
626 int maxX = 0;
627 int maxY = 0;
628 int maxZ = 0;
629 int newX = xN - 1;
630 int newY = yN - 1;
631 int newZ = zN - 1;
632 for (int iX = 0; iX < xN; iX++) {
633 for (int iY = 0; iY < yN; iY++) {
634 for (int iZ = 0; iZ < zN; iZ++) {
635 latticeR[1] = iX;
636 latticeR[2] = iY;
637 latticeR[3] = iZ;
638 auto physR = getPhysR(latticeR);
639 indicatorF(inside,physR.data());
640 if (inside[0]) {
641 fullCells++;
642 maxX = util::max(maxX, iX);
643 maxY = util::max(maxY, iY);
644 maxZ = util::max(maxZ, iZ);
645 newX = util::min(newX, iX);
646 newY = util::min(newY, iY);
647 newZ = util::min(newZ, iZ);
648 }
649 }
650 }
651 }
652 if (fullCells > 0) {
653 get(iC).setWeight(fullCells);
654 _cuboids[iC].resize({newX, newY, newZ}, {maxX - newX + 1, maxY - newY + 1, maxZ - newZ + 1});
655 }
656 else {
657 remove(iC);
658 }
659 } else {
660 LatticeR<D+1> latticeR{};
661 bool inside[1] {};
662
663 latticeR[0] = iC;
664 std::size_t fullCells = 0;
665 int xN = get(iC).getNx();
666 int yN = get(iC).getNy();
667 int maxX = 0;
668 int maxY = 0;
669 int newX = xN - 1;
670 int newY = yN - 1;
671 for (int iX = 0; iX < xN; iX++) {
672 for (int iY = 0; iY < yN; iY++) {
673 latticeR[1] = iX;
674 latticeR[2] = iY;
675 auto physR = getPhysR(latticeR);
676 indicatorF(inside,physR.data());
677 if (inside[0]) {
678 fullCells++;
679 maxX = util::max(maxX, iX);
680 maxY = util::max(maxY, iY);
681 newX = util::min(newX, iX);
682 newY = util::min(newY, iY);
683 }
684 }
685 }
686 if (fullCells > 0) {
687 get(iC).setWeight(fullCells);
688 _cuboids[iC].resize({newX, newY}, {maxX - newX + 1, maxY - newY + 1});
689 }
690 else {
691 remove(iC);
692 }
693 }
694}
Expr min(Expr a, Expr b)
Definition expr.cpp:249
Expr max(Expr a, Expr b)
Definition expr.cpp:245

References olb::Vector< T, Size >::data(), olb::util::max(), and olb::util::min().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ size()

template<typename T , unsigned D>
int olb::CuboidDecomposition< T, D >::size ( ) const

Returns number of cuboids in decomposition.

Definition at line 86 of file cuboidDecomposition.hh.

86 {
87 OLB_PRECONDITION(_cuboids.size() < std::numeric_limits<int>::max());
88 return static_cast<int>(_cuboids.size());
89}
#define OLB_PRECONDITION(COND)
Definition olbDebug.h:46

References OLB_PRECONDITION.

+ Here is the caller graph for this function:

◆ split()

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::split ( int iC,
int p )

Splits cuboid iC, removes it and adds p cuboids of same volume.

Definition at line 748 of file cuboidDecomposition.hh.

749{
750 Cuboid<T,D> temp(_cuboids[iC]);
751 temp.divideP(p, _cuboids);
752 remove(iC);
753}

References olb::Cuboid< T, D >::divideP().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ splitByWeight()

template<typename T , unsigned D>
requires (D == 3)
void olb::CuboidDecomposition< T, D >::splitByWeight ( int iC,
int p,
IndicatorF< T, D > & indicatorF )

Splits cuboid iC, removes it and adds p cuboids of same weight.

Definition at line 767 of file cuboidDecomposition.hh.

768{
769 T averageWeight = get(iC).getWeight() / (T) p;
770 Cuboid<T,D> temp(_cuboids[iC]);
771
772 int latticeR[4];
773 latticeR[0] = iC;
774 int xN = get(iC).getNx();
775 int yN = get(iC).getNy();
776 int zN = get(iC).getNz();
777 T deltaR = get(iC).getDeltaR();
778 int fullCells = 0;
779
780 Vector<T, 3> globPos_child = get(iC).getOrigin();
781 std::vector<int> extend_child = {xN, yN, zN};
782 int localPos_child = 0;
783
784 // looking for largest extend, because halfing the cuboid by its largest extend will result in the smallest surface and therfore in the least comminication cells
785 if ( get(iC).getNx() >= get(iC).getNy() && get(iC).getNx() >= get(iC).getNz()) {
786 // clout << "Cut in x direction!" << std::endl;
787
788 // for each child cuboid search for the optimal cutting plane
789 for ( int iChild = 0; iChild < p - 1; iChild++) {
790 fullCells = 0;
791 int fullCells_minusOne = 0;
792
793 for (int iX = localPos_child; iX < xN; iX++) {
794 fullCells_minusOne = fullCells;
795 for (int iY = 0; iY < yN; iY++) {
796 for (int iZ = 0; iZ < zN; iZ++) {
797 latticeR[1] = iX;
798 latticeR[2] = iY;
799 latticeR[3] = iZ;
800 auto physR = getPhysR(latticeR);
801 bool inside[1];
802 indicatorF(inside,physR.data());
803 if (inside[0]) {
804 fullCells++;
805 }
806 }
807 }
808 // the optimal cutting plane is determined, so that the child cuboid's cells inside the indicator are the closest to the total cells inside the indicator per number of children
809 if ( fullCells >= averageWeight ) {
810 if ( (fullCells - averageWeight) > (averageWeight - fullCells_minusOne) ) {
811 iX--;
812 }
813 // clout << "found optimal iX = " << iX << std::endl;
814 extend_child[0] = iX - localPos_child + 1;
815
816 Cuboid<T,D> child(globPos_child, deltaR, extend_child);
817 _cuboids.push_back(child);
818
819 globPos_child[0] += extend_child[0]*deltaR;
820 localPos_child += extend_child[0] + 1;
821 // clout << "added child " << iChild << " of " << p << std::endl;
822
823 break;
824 }
825 }
826
827 }
828
829 extend_child[0] = xN - localPos_child + p - 1;
830
831 Cuboid<T,D> child(globPos_child, deltaR, extend_child);
832 _cuboids.push_back(child);
833
834 // clout << "added last child of " << p << std::endl;
835
836 }
837 else if ( get(iC).getNy() >= get(iC).getNx() && get(iC).getNy() >= get(iC).getNz()) {
838 // clout << "Cut in y direction!" << std::endl;
839
840 for ( int iChild = 0; iChild < p - 1; iChild++) {
841 fullCells = 0;
842 int fullCells_minusOne = 0;
843
844 for (int iY = localPos_child; iY < yN; iY++) {
845 fullCells_minusOne = fullCells;
846 for (int iX = 0; iX < xN; iX++) {
847 for (int iZ = 0; iZ < zN; iZ++) {
848 latticeR[1] = iX;
849 latticeR[2] = iY;
850 latticeR[3] = iZ;
851 auto physR = getPhysR(latticeR);
852 bool inside[1];
853 indicatorF(inside,physR.data());
854 if (inside[0]) {
855 fullCells++;
856 }
857 }
858 }
859 if ( fullCells >= averageWeight ) {
860 if ( (fullCells - averageWeight) > (averageWeight - fullCells_minusOne) ) {
861 iY--;
862 }
863 // clout << "found optimal iY = " << iY << std::endl;
864 extend_child[1] = iY - localPos_child + 1;
865
866 Cuboid<T,D> child(globPos_child, deltaR, extend_child);
867 _cuboids.push_back(child);
868
869 globPos_child[1] += extend_child[1]*deltaR;
870 localPos_child += extend_child[1] + 1;
871 // clout << "added child " << iChild << " of " << p << std::endl;
872
873 break;
874 }
875 }
876
877 }
878
879 extend_child[1] = yN - localPos_child + p - 1;
880
881 Cuboid<T,D> child(globPos_child, deltaR, extend_child);
882 _cuboids.push_back(child);
883
884 // clout << "added last child of " << p << std::endl;
885 }
886 else {
887 // clout << "Cut in z direction!" << std::endl;
888
889 for ( int iChild = 0; iChild < p - 1; iChild++) {
890 fullCells = 0;
891 int fullCells_minusOne = 0;
892
893 for (int iZ = localPos_child; iZ < zN; iZ++) {
894 fullCells_minusOne = fullCells;
895 for (int iY = 0; iY < yN; iY++) {
896 for (int iX = 0; iX < xN; iX++) {
897 latticeR[1] = iX;
898 latticeR[2] = iY;
899 latticeR[3] = iZ;
900 auto physR = getPhysR(latticeR);
901 bool inside[1];
902 indicatorF(inside,physR.data());
903 if (inside[0]) {
904 fullCells++;
905 }
906 }
907 }
908 if ( fullCells >= averageWeight ) {
909 if ( (fullCells - averageWeight) > (averageWeight - fullCells_minusOne) ) {
910 iZ--;
911 }
912 // clout << "found optimal iZ = " << iZ << std::endl;
913 extend_child[2] = iZ - localPos_child + 1;
914
915 Cuboid<T,D> child(globPos_child, deltaR, extend_child);
916 _cuboids.push_back(child);
917
918 globPos_child[2] += extend_child[2]*deltaR;
919 localPos_child += extend_child[2] + 1;
920 // clout << "added child " << iChild << " of " << p << std::endl;
921
922 break;
923 }
924 }
925
926 }
927
928 extend_child[2] = zN - localPos_child + p - 1;
929
930 Cuboid<T,D> child(globPos_child, deltaR, extend_child);
931 _cuboids.push_back(child);
932
933 // clout << "added last child of " << p << std::endl;
934 }
935}

References olb::Vector< T, Size >::data().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ splitFractional()

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::splitFractional ( int iC,
int iD,
std::vector< T > fractions )

Splits cuboid iC along dimension iD into cuboids of fractions.

Definition at line 938 of file cuboidDecomposition.hh.

939{
940 Cuboid<T,D> tmp = _cuboids[iC];
941 tmp.divideFractional(iD, fractions, _cuboids);
942 remove(iC);
943}

References olb::Cuboid< T, D >::divideFractional().

+ Here is the call graph for this function:

◆ splitRegular()

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::splitRegular ( int iC,
int width )

Splits cuboid iC, removes it, adds approx. width^3 sized new cuboids.

Definition at line 756 of file cuboidDecomposition.hh.

757{
758 Cuboid<T,D> temp(_cuboids[iC]);
759 const int p = std::max(1, temp.getNx() / width);
760 const int q = std::max(1, temp.getNy() / width);
761 const int r = std::max(1, temp.getNz() / width);
762 temp.divide({p, q, r}, _cuboids);
763 remove(iC);
764}
constexpr int q() any_platform
Definition functions.h:140

References olb::Cuboid< T, D >::divide(), olb::Cuboid< T, D >::getNx(), olb::Cuboid< T, D >::getNy(), and olb::Cuboid< T, D >::getNz().

+ Here is the call graph for this function:

◆ tryRefineTo()

template<typename T , unsigned D>
bool olb::CuboidDecomposition< T, D >::tryRefineTo ( T deltaR)

Tries to refine mesh to given deltaR.

Definition at line 734 of file cuboidDecomposition.hh.

735{
736 const T tolerance = std::numeric_limits<T>::epsilon();
737 const T currDeltaR = _motherCuboid.getDeltaR();
738 const int factor = std::ceil(currDeltaR / goalDeltaR);
739 if (util::fabs(currDeltaR / factor - goalDeltaR) < tolerance) {
740 refine(factor);
741 return true;
742 } else {
743 return false;
744 }
745}
void refine(int factor)
Refines mesh by splitting each cell into factor^3 cells.
Expr fabs(Expr x)
Definition expr.cpp:230

References olb::util::fabs().

+ Here is the call graph for this function:

◆ writeToExistingFile()

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::writeToExistingFile ( std::string completeFileName,
LoadBalancer< T > & loadBalancer )

Save CuboidDecomposition into an existing XML File.

Definition at line 1006 of file cuboidDecomposition.hh.

1007{
1008 OstreamManager clout(std::cout, "CuboidDecomposition");
1009 std::ofstream fout;
1010 fout.flags(std::ios::scientific);
1011 fout.precision (std::numeric_limits<double>::digits10 + 1);
1012 if ( singleton::mpi().isMainProcessor() ) {
1013
1014 // Open File
1015 fout.open(completeFileName.c_str(), std::ios::app);
1016 if (!fout) {
1017 clout << "Error: could not open " << completeFileName << std::endl;
1018 }
1019
1020 // --- Preamble --- //
1021 fout << "<CuboidDecomposition dimension=\"3\" ";
1022 getMotherCuboid().writeAsXML(fout);
1023 fout << ">\n";
1024
1025 // TODO: Move Cuboid XML Serialization to Cuboid3D class
1026 for (int iC = 0; iC < size(); ++iC) {
1027 fout << "<Cuboid ";
1028 get(iC).writeAsXML(fout);
1029 fout << " />\n";
1030 }
1031
1032 fout << "</CuboidDecomposition>\n";
1033
1034 fout.close();
1035 }
1036}
MpiManager & mpi()

References olb::singleton::mpi().

+ Here is the call graph for this function:

◆ writeToFile()

template<typename T , unsigned D>
void olb::CuboidDecomposition< T, D >::writeToFile ( std::string fileName,
LoadBalancer< T > & loadBalancer )

Save CuboidDecomposition into XML File.

Definition at line 1040 of file cuboidDecomposition.hh.

1041{
1042 std::string fname = singleton::directories().getLogOutDir() + fileName + ".xml";
1043 std::ofstream fout;
1044 if (singleton::mpi().isMainProcessor()) {
1045 fout.open(fname.c_str(), std::ios::trunc);
1046 fout << "<?xml version=\"1.0\"?>\n";
1047 fout << "<XMLContent>\n";
1048 fout.close();
1049 fout.clear();
1050 }
1051
1052 writeToExistingFile(fname, loadBalancer);
1053
1054 if (singleton::mpi().isMainProcessor()) {
1055 fout.open(fname.c_str(), std::ios::app);
1056 fout << "</XMLContent>\n";
1057 fout.close();
1058 }
1059}
void writeToExistingFile(std::string completeFileName, LoadBalancer< T > &loadBalancer)
Save CuboidDecomposition into an existing XML File.
std::string getLogOutDir() const
Definition singleton.h:95
Directories & directories()
Definition singleton.h:162

References olb::singleton::directories(), olb::singleton::Directories::getLogOutDir(), and olb::singleton::mpi().

+ Here is the call graph for this function:

The documentation for this class was generated from the following files: