OpenLB 1.8.1
Loading...
Searching...
No Matches
olb::refinement::lagrava Namespace Reference

Implementation of a simplified version of the refinement algorithm by Lagrava et al. More...

Classes

struct  FineToCoarseO
 
struct  FullTimeCoarseToFineO
 
struct  HalfTimeCoarseToFineO
 
struct  InitializeO
 

Functions

template<typename T , typename DESCRIPTOR >
std::unique_ptr< SuperLatticeRefinement< T, DESCRIPTOR > > makeCoarseToFineCoupler (SuperLattice< T, DESCRIPTOR > &sLatticeCoarse, SuperGeometry< T, DESCRIPTOR::d > &sGeometryCoarse, SuperLattice< T, DESCRIPTOR > &sLatticeFine, SuperGeometry< T, DESCRIPTOR::d > &sGeometryFine)
 
template<typename T , typename DESCRIPTOR >
std::unique_ptr< SuperLatticeRefinement< T, DESCRIPTOR > > makeFineToCoarseCoupler (SuperLattice< T, DESCRIPTOR > &sLatticeCoarse, SuperGeometry< T, DESCRIPTOR::d > &sGeometryCoarse, SuperLattice< T, DESCRIPTOR > &sLatticeFine, SuperGeometry< T, DESCRIPTOR::d > &sGeometryFine)
 

Detailed Description

Implementation of a simplified version of the refinement algorithm by Lagrava et al.

DOI: 10.1016/j.jcp.2012.03.015

Function Documentation

◆ makeCoarseToFineCoupler()

template<typename T , typename DESCRIPTOR >
std::unique_ptr< SuperLatticeRefinement< T, DESCRIPTOR > > olb::refinement::lagrava::makeCoarseToFineCoupler ( SuperLattice< T, DESCRIPTOR > & sLatticeCoarse,
SuperGeometry< T, DESCRIPTOR::d > & sGeometryCoarse,
SuperLattice< T, DESCRIPTOR > & sLatticeFine,
SuperGeometry< T, DESCRIPTOR::d > & sGeometryFine )

Definition at line 261 of file lagrava.h.

266{
267 auto& loadBalancerFine = dynamic_cast<RefinedLoadBalancer<T,DESCRIPTOR::d>&>(
268 sLatticeFine.getLoadBalancer());
269 auto& loadBalancerCoarse = sLatticeCoarse.getLoadBalancer();
270 auto& cDecompositionFine = sLatticeFine.getCuboidDecomposition();
271 const auto& converterCoarse = sLatticeCoarse.getConverter();
272
273 SuperIndicatorDomainFrontierDistanceF<T,DESCRIPTOR> c2fFrontierI(cDecompositionFine,
274 sGeometryFine,
275 0);
276 SuperIndicatorDomainFrontierDistanceF<T,DESCRIPTOR> c2fInsideI(cDecompositionFine,
277 sGeometryFine,
278 1);
279 SuperIndicatorDomainFrontierDistanceF<T,DESCRIPTOR> c2fOutsideI(cDecompositionFine,
280 sGeometryFine,
281 -1);
282
283 auto coarseToFine = std::make_unique<SuperLatticeRefinement<T,DESCRIPTOR>>(sLatticeCoarse,
284 sLatticeFine,
285 loadBalancerFine);
286 auto& coarseToFineCommunicatorCoarse = coarseToFine->getCoarseCommunicator(meta::id<FullTimeCoarseToFineO>{});
287 coarseToFineCommunicatorCoarse.template requestField<descriptors::POPULATION>();
288
289 for (int iC = 0; iC < loadBalancerFine.size(); ++iC) {
290 auto& fBlock = sLatticeFine.getBlock(iC);
291
292 fBlock.forSpatialLocations([&](LatticeR<DESCRIPTOR::d> fineLatticeR) {
293 if (c2fFrontierI.getBlockIndicatorF(iC)(fineLatticeR)) {
294 if (fBlock.isInsideCore(fineLatticeR)) {
295 coarseToFine->getBlock(iC).add(fineLatticeR);
296 } else {
297 // Couple co-incident nodes in overlap s.t. context data for interpolation is available
298 if (fineLatticeR % 2 == Vector<int,DESCRIPTOR::d>(0)) {
299 coarseToFine->getBlock(iC).add(fineLatticeR);
300
301 // Coarse populations need to be up to date for FullTimeCoarseToFineO
302 auto coarseLatticeR = (fineLatticeR / 2).withPrefix(
303 loadBalancerCoarse.glob(loadBalancerFine.cloc(iC)));
304 coarseToFineCommunicatorCoarse.requestCell(coarseLatticeR);
305 }
306 }
307 }
308 });
309
310 auto& insideI = c2fInsideI.getBlockIndicatorF(iC);
311 auto& outsideI = c2fOutsideI.getBlockIndicatorF(iC);
312
313 fBlock.forSpatialLocations([&](LatticeR<DESCRIPTOR::d> fineLatticeR) {
314 if (auto index = coarseToFine->getBlock(iC).getDataIndex(fineLatticeR)) {
315 auto [type, normal] = computeBoundaryTypeAndNormal(insideI, outsideI, fineLatticeR);
316 coarseToFine->getBlock(iC).getData()
317 .template getField<fields::refinement::NORMAL>().set(*index, normal);
318 }
319 });
320 fBlock.defineDynamics(outsideI, meta::id<NoDynamics<T,DESCRIPTOR>>{});
321
322 coarseToFine->getBlock(iC).getData()
323 .template getData<OperatorParameters<refinement::lagrava::HalfTimeCoarseToFineO>>()
324 .template set<descriptors::TAU>(converterCoarse.getLatticeRelaxationTime());
325 coarseToFine->getBlock(iC).getData()
326 .template getData<OperatorParameters<refinement::lagrava::FullTimeCoarseToFineO>>()
327 .template set<descriptors::TAU>(converterCoarse.getLatticeRelaxationTime());
328
329 }
330
331 coarseToFineCommunicatorCoarse.exchangeRequests();
332 coarseToFine->setProcessingContext(ProcessingContext::Simulation);
333
334 return coarseToFine;
335}
Load balancer for refined lattice hierarchies.
const UnitConverter< T, DESCRIPTOR > & getConverter() const
LoadBalancer< T > & getLoadBalancer()
Read and write access to the load balancer.
CuboidDecomposition< T, D > & getCuboidDecomposition()
Read and write access to cuboid geometry.
Plain old scalar vector.
Distribution< T > normal(T mean, T stddev)
std::pair< DiscreteNormalType, Vector< int, 2 > > computeBoundaryTypeAndNormal(BlockIndicatorF2D< T > &fluidI, BlockIndicatorF2D< T > &outsideI, Vector< int, 2 > latticeR)
Returns type (e.g. edge / corner) and discrete normal in 2D.
Indicator to identify a cell layer at given distance from the cuboid decomposition's frontier.
Definition indicator.h:37
Identity type to pass non-constructible types as value.
Definition meta.h:79

References olb::computeBoundaryTypeAndNormal(), olb::BlockStructureD< D >::forSpatialLocations(), olb::SuperLattice< T, DESCRIPTOR >::getBlock(), olb::SuperLattice< T, DESCRIPTOR >::getConverter(), olb::SuperStructure< T, D >::getCuboidDecomposition(), olb::SuperStructure< T, D >::getLoadBalancer(), and olb::Simulation.

+ Here is the call graph for this function:

◆ makeFineToCoarseCoupler()

template<typename T , typename DESCRIPTOR >
std::unique_ptr< SuperLatticeRefinement< T, DESCRIPTOR > > olb::refinement::lagrava::makeFineToCoarseCoupler ( SuperLattice< T, DESCRIPTOR > & sLatticeCoarse,
SuperGeometry< T, DESCRIPTOR::d > & sGeometryCoarse,
SuperLattice< T, DESCRIPTOR > & sLatticeFine,
SuperGeometry< T, DESCRIPTOR::d > & sGeometryFine )

Definition at line 338 of file lagrava.h.

343{
344 auto& loadBalancerFine = dynamic_cast<RefinedLoadBalancer<T,DESCRIPTOR::d>&>(
345 sLatticeFine.getLoadBalancer());
346 auto& cDecompositionFine = sLatticeFine.getCuboidDecomposition();
347 const auto& converterCoarse = sLatticeCoarse.getConverter();
348
349 SuperIndicatorDomainFrontierDistanceF<T,DESCRIPTOR> f2cFrontierI(cDecompositionFine,
350 sGeometryFine,
351 2);
352
353 auto fineToCoarse = std::make_unique<SuperLatticeRefinement<T,DESCRIPTOR>>(
354 sLatticeCoarse, sLatticeFine, loadBalancerFine);
355 for (int iC = 0; iC < loadBalancerFine.size(); ++iC) {
356 auto& cBlock = sLatticeCoarse.getBlock(loadBalancerFine.cloc(iC));
357
358 cBlock.forCoreSpatialLocations([&](LatticeR<DESCRIPTOR::d> coarseLatticeR) {
359 if (f2cFrontierI.getBlockIndicatorF(iC)(2*coarseLatticeR)) {
360 fineToCoarse->getBlock(iC).add(2*coarseLatticeR);
361 }
362 });
363 fineToCoarse->getBlock(iC).getData()
364 .template getData<OperatorParameters<refinement::lagrava::FineToCoarseO>>()
365 .template set<descriptors::TAU>(converterCoarse.getLatticeRelaxationTime());
366 }
367
368 fineToCoarse->setProcessingContext(ProcessingContext::Simulation);
369
370 return fineToCoarse;
371}

References olb::BlockStructureD< D >::forCoreSpatialLocations(), olb::SuperLattice< T, DESCRIPTOR >::getBlock(), olb::SuperLattice< T, DESCRIPTOR >::getConverter(), olb::SuperStructure< T, D >::getCuboidDecomposition(), olb::SuperStructure< T, D >::getLoadBalancer(), and olb::Simulation.

+ Here is the call graph for this function: