Commit 96e67973 authored by Dennis Gläser's avatar Dennis Gläser
Browse files

allow for solution dependent fluxes when using global caching

this commit furthermore introduces that the problem is given to the global containers
for volume variables and flux variables in the constructor.
parent bc57df8b
......@@ -62,6 +62,8 @@ class CCLocalAssembler<TypeTag,
enum { numEq = GET_PROP_VALUE(TypeTag, NumEq) };
static constexpr bool enableGlobalFluxVarsCache = GET_PROP_VALUE(TypeTag, EnableGlobalFluxVariablesCache);
public:
/*!
......@@ -331,6 +333,9 @@ private:
// update the volume variables and the flux var cache
curVolVars.update(elemSol, problem, element, scv);
if (enableGlobalFluxVarsCache)
gridVariables.gridFluxVarsCache().updateElement(element, fvGeometry, curElemVolVars);
else
elemFluxVarsCache.update(element, fvGeometry, curElemVolVars);
// calculate the residual with the deflected primary variables
......@@ -390,6 +395,9 @@ private:
// update the volume variables and the flux var cache
curVolVars.update(elemSol, problem, element, scv);
if (enableGlobalFluxVarsCache)
gridVariables.gridFluxVarsCache().updateElement(element, fvGeometry, curElemVolVars);
else
elemFluxVarsCache.update(element, fvGeometry, curElemVolVars);
// calculate the residual with the deflected primary variables and subtract it
......@@ -861,7 +869,6 @@ private:
// update the volume variables and the flux var cache
curVolVars.update(elemSol, problem, element, scv);
elemFluxVarsCache.update(element, fvGeometry, curElemVolVars);
// calculate the residual with the deflected primary variables and subtract it
if (!isGhost)
......
......@@ -58,13 +58,16 @@ class BoxGlobalFluxVariablesCache<TypeTag, true>
using FVElementGeometry = typename GET_PROP_TYPE(TypeTag, FVElementGeometry);
public:
void update(const Problem& problem,
const FVGridGeometry& fvGridGeometry,
BoxGlobalFluxVariablesCache(const Problem& problem) : problemPtr_(&problem) {}
void update(const FVGridGeometry& fvGridGeometry,
const GridVolumeVariables& gridVolVars,
const SolutionVector& sol)
const SolutionVector& sol,
bool forceUpdate = false)
{
// Here, we do not do anything unless it is a forced update
if (forceUpdate)
{
problemPtr_ = &problem;
fluxVarsCache_.resize(fvGridGeometry.gridView().size(0));
for (const auto& element : elements(fvGridGeometry.gridView()))
{
......@@ -78,7 +81,8 @@ public:
fluxVarsCache_[eIdx].resize(fvGeometry.numScvf());
for (auto&& scvf : scvfs(fvGeometry))
cache(eIdx, scvf.index()).update(problem, element, fvGeometry, elemVolVars, scvf);
cache(eIdx, scvf.index()).update(problem(), element, fvGeometry, elemVolVars, scvf);
}
}
}
......@@ -128,12 +132,12 @@ class BoxGlobalFluxVariablesCache<TypeTag, false>
using FVElementGeometry = typename GET_PROP_TYPE(TypeTag, FVElementGeometry);
public:
BoxGlobalFluxVariablesCache(const Problem& problem) : problemPtr_(&problem) {}
void update(const Problem& problem,
const FVGridGeometry& fvGridGeometry,
void update(const FVGridGeometry& fvGridGeometry,
const GridVolumeVariables& gridVolVars,
const SolutionVector& sol)
{ problemPtr_ = &problem; }
const SolutionVector& sol,
bool forceUpdate = false) {}
/*!
* \brief Return a local restriction of this global object
......
......@@ -56,10 +56,10 @@ class BoxGlobalVolumeVariables<TypeTag,/*enableGlobalVolVarCache*/true>
using Element = typename GridView::template Codim<0>::Entity;
public:
void update(const Problem& problem, const FVGridGeometry& fvGridGeometry, const SolutionVector& sol)
{
problemPtr_ = &problem;
BoxGlobalVolumeVariables(const Problem& problem) : problemPtr_(&problem) {}
void update(const FVGridGeometry& fvGridGeometry, const SolutionVector& sol)
{
volumeVariables_.resize(fvGridGeometry.gridView().size(0));
for (const auto& element : elements(fvGridGeometry.gridView()))
{
......@@ -77,7 +77,7 @@ public:
// update the volvars of the element
volumeVariables_[eIdx].resize(fvGeometry.numScv());
for (auto&& scv : scvs(fvGeometry))
volumeVariables_[eIdx][scv.indexInElement()].update(elemSol, problem, element, scv);
volumeVariables_[eIdx][scv.indexInElement()].update(elemSol, problem(), element, scv);
}
}
......@@ -115,9 +115,9 @@ class BoxGlobalVolumeVariables<TypeTag, /*enableGlobalVolVarCache*/false>
using FVGridGeometry = typename GET_PROP_TYPE(TypeTag, FVGridGeometry);
public:
BoxGlobalVolumeVariables(const Problem& problem) : problemPtr_(&problem) {}
void update(const Problem& problem, const FVGridGeometry& fvGridGeometry, const SolutionVector& sol)
{ problemPtr_ = &problem; }
void update(const FVGridGeometry& fvGridGeometry, const SolutionVector& sol) {}
/*!
* \brief Return a local restriction of this global object
......
......@@ -55,10 +55,10 @@ class CCGlobalVolumeVariables<TypeTag, /*enableGlobalVolVarsCache*/true>
using Element = typename GridView::template Codim<0>::Entity;
public:
void update(const Problem& problem, const FVGridGeometry& fvGridGeometry, const SolutionVector& sol)
{
problemPtr_ = &problem;
CCGlobalVolumeVariables(const Problem& problem) : problemPtr_(&problem) {}
void update(const FVGridGeometry& fvGridGeometry, const SolutionVector& sol)
{
const auto numScv = fvGridGeometry.numScv();
const auto numBoundaryScvf = fvGridGeometry.numBoundaryScvf();
......@@ -71,7 +71,7 @@ public:
for (auto&& scv : scvs(fvGeometry))
{
const ElementSolution elemSol({sol[scv.dofIndex()]});
volumeVariables_[scv.dofIndex()].update(elemSol, problem, element, scv);
volumeVariables_[scv.dofIndex()].update(elemSol, problem(), element, scv);
}
// handle the boundary volume variables
......@@ -82,15 +82,15 @@ public:
continue;
// check if boundary is a pure dirichlet boundary
const auto bcTypes = problem.boundaryTypes(element, scvf);
const auto bcTypes = problem().boundaryTypes(element, scvf);
if (bcTypes.hasOnlyDirichlet())
{
const auto insideScvIdx = scvf.insideScvIdx();
const auto& insideScv = fvGeometry.scv(insideScvIdx);
const ElementSolution dirichletPriVars({problem.dirichlet(element, scvf)});
const ElementSolution dirichletPriVars({problem().dirichlet(element, scvf)});
volumeVariables_[scvf.outsideScvIdx()].update(dirichletPriVars,
problem,
problem(),
element,
insideScv);
}
......@@ -132,7 +132,6 @@ public:
private:
const Problem* problemPtr_;
std::vector<VolumeVariables> volumeVariables_;
};
......@@ -147,8 +146,9 @@ class CCGlobalVolumeVariables<TypeTag, /*enableGlobalVolVarsCache*/false>
using FVGridGeometry = typename GET_PROP_TYPE(TypeTag, FVGridGeometry);
public:
void update(const Problem& problem, const FVGridGeometry& fvGridGeometry, const SolutionVector& sol)
{ problemPtr_ = &problem; }
CCGlobalVolumeVariables(const Problem& problem) : problemPtr_(&problem) {}
void update(const FVGridGeometry& fvGridGeometry, const SolutionVector& sol) {}
/*!
* \brief Return a local restriction of this global object
......@@ -163,7 +163,6 @@ public:
{ return *problemPtr_;}
private:
const Problem* problemPtr_;
};
......
......@@ -82,7 +82,7 @@ public:
// access operators in the case of caching
const FluxVariablesCache& operator [](const SubControlVolumeFace& scvf) const
{ return (*globalFluxVarsCachePtr_)[scvf.index()]; }
{ return (*globalFluxVarsCachePtr_)[scvf]; }
//! The global object we are a restriction of
const GlobalFluxVariablesCache& globalFluxVarsCache() const
......@@ -99,7 +99,8 @@ private:
template<class TypeTag>
class CCMpfaElementFluxVariablesCache<TypeTag, false>
{
// the flux variables cache filler needs to be friend to fill the matrices
// the flux variables cache filler needs to be friend to fill
// the interaction volumes and data handles
friend CCMpfaFluxVariablesCacheFiller<TypeTag>;
using Problem = typename GET_PROP_TYPE(TypeTag, Problem);
......@@ -143,14 +144,11 @@ public:
clear_();
// some references for convenience
const auto& problem = globalFluxVarsCache().problem_();
const auto& problem = globalFluxVarsCache().problem();
const auto& fvGridGeometry = fvGeometry.fvGridGeometry();
// the global index the cache will be bound to
globalI_ = fvGridGeometry.elementMapper().index(element);
// the assembly map of the given element
const auto& assemblyMapI = fvGridGeometry.connectivityMap()[globalI_];
const auto& assemblyMapI = fvGridGeometry.connectivityMap()[fvGridGeometry.elementMapper().index(element)];
// reserve memory for scvf index container
unsigned int numNeighborScvfs = 0;
......@@ -186,7 +184,7 @@ public:
{
auto& scvfCache = fluxVarsCache_[i++];
if (!scvfCache.isUpdated())
filler.fill(*this, scvfCache, element, fvGeometry, elemVolVars, scvf);
filler.fill(*this, scvfCache, element, fvGeometry, elemVolVars, scvf, true);
}
for (const auto& dataJ : assemblyMapI)
......@@ -196,7 +194,7 @@ public:
{
auto& scvfCache = fluxVarsCache_[i++];
if (!scvfCache.isUpdated())
filler.fill(*this, scvfCache, elementJ, fvGeometry, elemVolVars, fvGeometry.scvf(scvfIdx));
filler.fill(*this, scvfCache, elementJ, fvGeometry, elemVolVars, fvGeometry.scvf(scvfIdx), true);
}
}
}
......@@ -210,24 +208,18 @@ public:
DUNE_THROW(Dune::NotImplemented, "Local element binding of the flux variables cache in mpfa schemes");
}
// This function updates the transmissibilities (e.g. after the solution has been deflected)
// This function is used to update the transmissibilities if the volume variables have changed
// Results in undefined behaviour if called before bind() or with a different element
void update(const Element& element,
const FVElementGeometry& fvGeometry,
const ElementVolumeVariables& elemVolVars)
{
// make sure this is not called for a different element than a previous bind()
assert(globalI_ == fvGeometry.gridFvGeometry().elementMapper().index(element)
&& "The element flux variables cache can only be updated for the element it was bound to");
// ask for solution dependency only once per simulation
static const bool isSolDependent = FluxVariablesCacheFiller::isSolutionDependent();
// update only if transmissibilities are solution-dependent
if (isSolDependent)
if (FluxVariablesCacheFiller::isSolDependent)
{
const auto& problem = globalFluxVarsCache().problem_();
const auto& problem = globalFluxVarsCache().problem();
const auto& fvGridGeometry = fvGeometry.fvGridGeometry();
const auto& assemblyMapI = fvGridGeometry.connectivityMap()[globalI_];
const auto& assemblyMapI = fvGridGeometry.connectivityMap()[fvGridGeometry.elementMapper().index(element)];
// helper class to fill flux variables caches
FluxVariablesCacheFiller filler(problem);
......@@ -242,7 +234,7 @@ public:
{
auto& scvfCache = fluxVarsCache_[i++];
if (!scvfCache.isUpdated())
filler.update(*this, scvfCache, element, fvGeometry, elemVolVars, scvf);
filler.fill(*this, scvfCache, element, fvGeometry, elemVolVars, scvf);
}
for (const auto& dataJ : assemblyMapI)
......@@ -252,7 +244,7 @@ public:
{
auto& scvfCache = fluxVarsCache_[i++];
if (!scvfCache.isUpdated())
filler.update(*this, scvfCache, elementJ, fvGeometry, elemVolVars, fvGeometry.scvf(scvfIdx));
filler.fill(*this, scvfCache, elementJ, fvGeometry, elemVolVars, fvGeometry.scvf(scvfIdx));
}
}
}
......@@ -316,8 +308,6 @@ private:
return std::distance(globalScvfIndices_.begin(), it);
}
// the global index of the actual bound element
IndexType globalI_;
// the local flux vars caches and the index set
std::vector<FluxVariablesCache> fluxVarsCache_;
......
......@@ -65,6 +65,10 @@ class CCMpfaFluxVariablesCacheFiller
static constexpr bool soldependentHeatConduction = GET_PROP_VALUE(TypeTag, SolutionDependentHeatConduction);
public:
static constexpr bool isSolDependent = (doAdvection && soldependentAdvection) ||
(doDiffusion && soldependentDiffusion) ||
(doHeatConduction && soldependentHeatConduction);
//! The constructor. Sets the problem pointer
CCMpfaFluxVariablesCacheFiller(const Problem& problem) : problemPtr_(&problem) {}
......@@ -77,7 +81,7 @@ public:
* \param fvGeometry The finite volume geometry
* \param elemVolVars The element volume variables
* \param scvf The corresponding sub-control volume face
* \param doSubCaches Array of bools indicating which sub caches have to be updated
* \param forceUpdateAll if true, forces all caches to be updated (even the solution-independent ones)
*/
template<class FluxVariablesCacheContainer>
void fill(FluxVariablesCacheContainer& fluxVarsCacheContainer,
......@@ -86,7 +90,7 @@ public:
const FVElementGeometry& fvGeometry,
const ElementVolumeVariables& elemVolVars,
const SubControlVolumeFace& scvf,
bool isUpdate = false)
bool forceUpdateAll = false)
{
// Set pointers
elementPtr_ = &element;
......@@ -98,7 +102,7 @@ public:
const auto& fvGridGeometry = fvGeometry.fvGridGeometry();
if (fvGridGeometry.vertexUsesSecondaryInteractionVolume(scvf.vertexIndex()))
{
if (!isUpdate)
if (forceUpdateAll)
{
// the local index of the interaction volume to be created in its container
const auto ivIndexInContainer = fluxVarsCacheContainer.secondaryInteractionVolumes_.size();
......@@ -118,7 +122,7 @@ public:
*ivDataHandle_);
// fill the caches for all the scvfs in the interaction volume
fillCachesInInteractionVolume_(fluxVarsCacheContainer, *secondaryIv_, *ivDataHandle_, ivIndexInContainer);
fillCachesInInteractionVolume_(fluxVarsCacheContainer, *secondaryIv_, *ivDataHandle_, ivIndexInContainer, true);
}
else
{
......@@ -127,12 +131,12 @@ public:
ivDataHandle_ = &fluxVarsCacheContainer.secondaryIvDataHandles_[ivIndexInContainer];
// fill the caches for all the scvfs in the interaction volume
fillCachesInInteractionVolume_(fluxVarsCacheContainer, *secondaryIv_, *ivDataHandle_, ivIndexInContainer, true);
fillCachesInInteractionVolume_(fluxVarsCacheContainer, *secondaryIv_, *ivDataHandle_, ivIndexInContainer);
}
}
else
{
if (!isUpdate)
if (forceUpdateAll)
{
// the local index of the interaction volume to be created in its container
const auto ivIndexInContainer = fluxVarsCacheContainer.primaryInteractionVolumes_.size();
......@@ -152,7 +156,7 @@ public:
*ivDataHandle_);
// fill the caches for all the scvfs in the interaction volume
fillCachesInInteractionVolume_(fluxVarsCacheContainer, *primaryIv_, *ivDataHandle_, ivIndexInContainer);
fillCachesInInteractionVolume_(fluxVarsCacheContainer, *primaryIv_, *ivDataHandle_, ivIndexInContainer, true);
}
else
{
......@@ -161,34 +165,9 @@ public:
ivDataHandle_ = &fluxVarsCacheContainer.primaryIvDataHandles_[ivIndexInContainer];
// fill the caches for all the scvfs in the interaction volume
fillCachesInInteractionVolume_(fluxVarsCacheContainer, *primaryIv_, *ivDataHandle_, ivIndexInContainer, true);
}
}
fillCachesInInteractionVolume_(fluxVarsCacheContainer, *primaryIv_, *ivDataHandle_, ivIndexInContainer);
}
/*!
* \brief function to update the flux variables caches during derivative calculation
*
* \copydoc fill
*/
template<class FluxVariablesCacheContainer>
void update(FluxVariablesCacheContainer& fluxVarsCacheContainer,
FluxVariablesCache& scvfFluxVarsCache,
const Element& element,
const FVElementGeometry& fvGeometry,
const ElementVolumeVariables& elemVolVars,
const SubControlVolumeFace& scvf)
{
// forward to fill routine
fill(fluxVarsCacheContainer, scvfFluxVarsCache, element, fvGeometry, elemVolVars, scvf, true);
}
static bool isSolutionDependent()
{
static const bool isSolDependent = (doAdvection && soldependentAdvection) ||
(doDiffusion && soldependentDiffusion) ||
(doHeatConduction && soldependentHeatConduction);
return isSolDependent;
}
const PrimaryInteractionVolume& primaryInteractionVolume() const
......@@ -223,12 +202,12 @@ private:
InteractionVolumeType& iv,
DataHandle& handle,
unsigned int ivIndexInContainer,
bool isUpdate = false)
bool forceUpdateAll = false)
{
// First we upate data which are not dependent on the physical processes.
// We store pointers to the other flux var caches, so that we have to obtain
// this data only once and can use it again in the sub-cache fillers.
if (!isUpdate)
if (forceUpdateAll)
{
std::vector<FluxVariablesCache*> ivFluxVarCaches(iv.globalLocalScvfPairedData().size());
unsigned int i = 0;
......@@ -306,8 +285,7 @@ private:
fillAdvection(FluxVariablesCacheContainer& fluxVarsCacheContainer,
InteractionVolumeType& iv,
DataHandle& handle,
const std::vector<FluxVariablesCache*>& ivFluxVarCaches)
{}
const std::vector<FluxVariablesCache*>& ivFluxVarCaches) {}
//! method to fill the diffusive quantities
template<class FluxVariablesCacheContainer, class InteractionVolumeType, bool diffusionEnabled = doDiffusion>
......@@ -362,8 +340,7 @@ private:
fillDiffusion(FluxVariablesCacheContainer& fluxVarsCacheContainer,
InteractionVolumeType& iv,
DataHandle& handle,
const std::vector<FluxVariablesCache*>& ivFluxVarCaches)
{}
const std::vector<FluxVariablesCache*>& ivFluxVarCaches) {}
//! method to fill the quantities related to heat conduction
template<class FluxVariablesCacheContainer, class InteractionVolumeType, bool heatConductionEnabled = doHeatConduction>
......@@ -404,8 +381,7 @@ private:
fillHeatConduction(FluxVariablesCacheContainer& fluxVarsCacheContainer,
InteractionVolumeType& iv,
DataHandle& handle,
const std::vector<FluxVariablesCache*>& ivFluxVarCaches)
{}
const std::vector<FluxVariablesCache*>& ivFluxVarCaches) {}
const Problem* problemPtr_;
const Element* elementPtr_;
......
......@@ -44,16 +44,18 @@ class CCMpfaGlobalFluxVariablesCache;
template<class TypeTag>
class CCMpfaGlobalFluxVariablesCache<TypeTag, true>
{
// the local class need access to the problem
friend typename GET_PROP_TYPE(TypeTag, ElementFluxVariablesCache);
// the filler needs access to the operators
// the flux variables cache filler needs to be friend to fill
// the interaction volumes and data handles
friend CCMpfaFluxVariablesCacheFiller<TypeTag>;
using Problem = typename GET_PROP_TYPE(TypeTag, Problem);
using GridView = typename GET_PROP_TYPE(TypeTag, GridView);
using Element = typename GridView::template Codim<0>::Entity;
using FVGridGeometry = typename GET_PROP_TYPE(TypeTag, FVGridGeometry);
using FVElementGeometry = typename GET_PROP_TYPE(TypeTag, FVElementGeometry);
using SolutionVector = typename GET_PROP_TYPE(TypeTag, SolutionVector);
using GridVolumeVariables = typename GET_PROP_TYPE(TypeTag, GlobalVolumeVariables);
using ElementVolumeVariables = typename GET_PROP_TYPE(TypeTag, ElementVolumeVariables);
using IndexType = typename GridView::IndexSet::IndexType;
using FluxVariablesCache = typename GET_PROP_TYPE(TypeTag, FluxVariablesCache);
using ElementFluxVariablesCache = typename GET_PROP_TYPE(TypeTag, ElementFluxVariablesCache);
......@@ -64,20 +66,22 @@ class CCMpfaGlobalFluxVariablesCache<TypeTag, true>
using FluxVariablesCacheFiller = CCMpfaFluxVariablesCacheFiller<TypeTag>;
public:
CCMpfaGlobalFluxVariablesCache(const Problem& problem) : problemPtr_(&problem) {}
// When global caching is enabled, precompute transmissibilities and stencils for all the scv faces
void update(const Problem& problem,
const FVGridGeometry& fvGridGeometry,
void update(const FVGridGeometry& fvGridGeometry,
const GridVolumeVariables& gridVolVars,
const SolutionVector& sol)
const SolutionVector& sol,
bool forceUpdate = false)
{
// only do the update if fluxes are solution dependent or if update is forced
if (FluxVariablesCacheFiller::isSolDependent || forceUpdate)
{
// clear data if forced update is desired
if (forceUpdate)
{
problemPtr_ = &problem;
// clear data
clear_();
// reserve memory estimate for caches, interaction volumes and corresponding data
fluxVarsCache_.resize(fvGridGeometry.numScvf());
const auto& gridIvIndexSets = fvGridGeometry.gridInteractionVolumeIndexSets();
const auto numPrimaryIvs = gridIvIndexSets.numPrimaryInteractionVolumes();
const auto numSecondaryIVs = gridIvIndexSets.numSecondaryInteractionVolumes();
......@@ -85,9 +89,13 @@ public:
secondaryInteractionVolumes_.reserve(numSecondaryIVs);
primaryIvDataHandles_.reserve(numPrimaryIvs);
secondaryIvDataHandles_.reserve(numSecondaryIVs);
}
// reserve memory estimate for caches, interaction volumes and corresponding data
fluxVarsCache_.resize(fvGridGeometry.numScvf());
// instantiate helper class to fill the caches
FluxVariablesCacheFiller filler(problem);
FluxVariablesCacheFiller filler(problem());
for (const auto& element : elements(fvGridGeometry.gridView()))
{
......@@ -101,7 +109,71 @@ public:
// prepare all the caches of the scvfs inside the corresponding interaction volume
for (const auto& scvf : scvfs(fvGeometry))
if (!fluxVarsCache_[scvf.index()].isUpdated())
filler.fill(*this, fluxVarsCache_[scvf.index()], element, fvGeometry, elemVolVars, scvf);
filler.fill(*this, fluxVarsCache_[scvf.index()], element, fvGeometry, elemVolVars, scvf, forceUpdate);
}
}
}
void updateElement(const Element& element,
const FVElementGeometry& fvGeometry,
const ElementVolumeVariables& elemVolVars)
{
// update only if transmissibilities are solution-dependent
if (FluxVariablesCacheFiller::isSolDependent)
{
const auto& fvGridGeometry = fvGeometry.fvGridGeometry();
const auto& assemblyMapI = fvGridGeometry.connectivityMap()[fvGridGeometry.elementMapper().index(element)];
// helper class to fill flux variables caches
FluxVariablesCacheFiller filler(problem());
// first, set all the caches to "outdated"
for (const auto& scvf : scvfs(fvGeometry))
fluxVarsCache_[scvf.index()].setUpdateStatus(false);
for (const auto& dataJ : assemblyMapI)
for (const auto scvfIdx : dataJ.scvfsJ)
fluxVarsCache_[scvfIdx].setUpdateStatus(false);
// go through the caches maybe update them
for (const auto& scvf : scvfs(fvGeometry))
{
auto& scvfCache = fluxVarsCache_[scvf.index()];
if (!scvfCache.isUpdated())
{
// reset the pointers to the local views in the corresponding interaction volume
const auto ivIndexInContainer = scvfCache.ivIndexInContainer();
if (fvGridGeometry.vertexUsesSecondaryInteractionVolume(scvf.vertexIndex()))
secondaryInteractionVolumes_[ivIndexInContainer].resetPointers(fvGeometry, elemVolVars);
else
primaryInteractionVolumes_[ivIndexInContainer].resetPointers(fvGeometry, elemVolVars);
// update cache
filler.fill(*this, scvfCache, element, fvGeometry, elemVolVars, scvf);
}
}
for (const auto& dataJ : assemblyMapI)
{
const auto elementJ = fvGridGeometry.element(dataJ.globalJ);
for (const auto scvfIdx : dataJ.scvfsJ)
{
auto& scvfCache = fluxVarsCache_[scvfIdx];
if (!scvfCache.isUpdated())
{
const auto& scvf = fvGeometry.scvf(scvfIdx);
const auto ivIndexInContainer = scvfCache.ivIndexInContainer();
// reset the pointers to the local views in the corresponding interaction volume
if (fvGridGeometry.vertexUsesSecondaryInteractionVolume(scvf.vertexIndex()))
secondaryInteractionVolumes_[ivIndexInContainer].resetPointers(fvGeometry, elemVolVars);
else
primaryInteractionVolumes_[ivIndexInContainer].resetPointers(fvGeometry, elemVolVars);
// update cache
filler.fill(*this, scvfCache, elementJ, fvGeometry, elemVolVars, scvf);
}
}
}
}
}
......@@ -113,6 +185,16 @@ public:
friend inline ElementFluxVariablesCache localView(const CCMpfaGlobalFluxVariablesCache& global)