Commit 0eeb3161 authored by Timo Koch's avatar Timo Koch
Browse files

[fvGeometry] Make range generators free functions / friend functions

We iterate over all scvs of a fvElementGeometry like this
for (const auto& scv : scvs(fvGeometry))
This is closer to the way we speak "For each scv in all scvs of the fvElementGeometry do..."
and analogously to how we iterate over elements of a gridView.
parent 2a63d3f4
......@@ -317,15 +317,15 @@ public:
auto fvGeometry = problem.model().fvGeometries(element);
const auto globalPos = source.position();
// loop over all sub control volumes and check if the point source is inside
std::vector<unsigned int> scvs;
for (auto&& scv : fvGeometry.scvs())
std::vector<unsigned int> scvIndices;
for (const auto& scv : scvs(fvGeometry))
{
if (BoundingBoxTreeHelper<dimworld>::pointInGeometry(scv.geometry(), globalPos))
scvs.push_back(scv.indexInElement());
scvIndices.push_back(scv.indexInElement());
}
// for all scvs that where tested positiv add the point sources
// to the element/scv to point source map
for (auto scvIdx : scvs)
for (auto scvIdx : scvIndices)
{
const auto key = std::make_pair(eIdx, scvIdx);
if (pointSourceMap.count(key))
......
......@@ -91,7 +91,7 @@ public:
// evaluate gradP - rho*g at integration point
DimVector gradP(0.0);
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
// the global shape function gradient
DimVector gradI;
......
......@@ -56,7 +56,7 @@ public:
const auto& elementGeometry = element.geometry();
const auto& localBasis = problem.model().fvGeometries().feLocalBasis(elementGeometry.type());
const auto& fvGeometry = problem.model().fvGeometries(element);
for (const auto& scvf : fvGeometry.scvfs())
for (const auto& scvf : scvfs(fvGeometry))
{
(*this)[scvf].update(problem, element, elementGeometry, localBasis, scvf);
}
......@@ -88,7 +88,7 @@ public:
const auto numScvf = fvGeometry.numScvf();
fluxVarsCache_.resize(numScvf);
IndexType localScvfIdx = 0;
for (const auto& scvf : fvGeometry.scvfs())
for (const auto& scvf : scvfs(fvGeometry))
fluxVarsCache_[localScvfIdx++].update(problem_(), element, elementGeometry, localBasis, scvf);
}
......
......@@ -144,13 +144,13 @@ public:
problem.model().fvGeometries_().bindElement(element);
const auto& fvGeometry = problem.model().fvGeometries(element);
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
auto vIdxGlobal = scv.dofIndex();
vertexStencils_[vIdxGlobal].vertexScvs().push_back(scv.index());
vertexStencils_[vIdxGlobal].elementIndices().push_back(eIdx);
for (const auto& scvJ : fvGeometry.scvs())
for (const auto& scvJ : scvs(fvGeometry))
{
auto vIdxGlobalJ = scvJ.dofIndex();
......
......@@ -79,7 +79,7 @@ public:
problem.model().fvGeometries_().bindElement(element);
const auto& fvGeometry = problem.model().fvGeometries(element);
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
(*this)[scv].update(sol[scv.dofIndex()],
problem,
......@@ -223,7 +223,7 @@ public:
}
// Update boundary volume variables
for (const auto& scvFace : fvGeometry.scvfs())
for (const auto& scvFace : scvfs(fvGeometry))
{
// if we are not on a boundary, skip the rest
if (!scvFace.boundary())
......@@ -306,7 +306,7 @@ public:
// volVarIndices_.resize(numDofs);
int localIdx = 0;
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
// std::cout << "scv index: " << scv.index() << ", dofIdx: " << scv.dofIndex() << ", localIdx: " << scv.indexInElement() << std::endl;
const auto& sol = problem_().model().curSol()[scv.dofIndex()];
......@@ -451,7 +451,7 @@ public:
// volVarIndices_.resize(numDofs);
int localIdx = 0;
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
const auto& sol = problem_().model().prevSol()[scv.dofIndex()];
// let the interface solver update the volvars
......
......@@ -56,7 +56,7 @@ public:
problem.model().fvGeometries_().bind(element);
const auto& fvGeometry = problem.model().fvGeometries(element);
for (const auto& scvf : fvGeometry.scvfs())
for (const auto& scvf : scvfs(fvGeometry))
{
(*this)[scvf].update(problem, element, scvf);
}
......@@ -84,7 +84,7 @@ public:
IndexType localScvfIdx = 0;
// fill the containers
for (const auto& scvf : fvGeometry.scvfs())
for (const auto& scvf : scvfs(fvGeometry))
{
fluxVarsCache_[localScvfIdx].update(problem_(), element, scvf);
globalScvfIndices_[localScvfIdx] = scvf.index();
......@@ -118,7 +118,7 @@ public:
fluxVarsCache_.resize(numScvf);
globalScvfIndices_.resize(numScvf);
IndexType localScvfIdx = 0;
for (const auto& scvf : fvGeometry.scvfs())
for (const auto& scvf : scvfs(fvGeometry))
{
fluxVarsCache_[localScvfIdx].update(problem_(), element, scvf);
globalScvfIndices_[localScvfIdx] = scvf.index();
......
......@@ -49,7 +49,7 @@ public:
const auto& fvGeometry = problem.model().fvGeometries(element);
// loop over sub control faces
for (const auto& scvf : fvGeometry.scvfs())
for (const auto& scvf : scvfs(fvGeometry))
{
FluxVariables fluxVars;
const auto& stencil = fluxVars.computeStencil(problem, element, scvf);
......
......@@ -78,7 +78,7 @@ public:
{
problem.model().fvGeometries_().bindElement(element);
const auto& fvGeometry = problem.model().fvGeometries(element);
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
(*this)[scv].update(sol[scv.dofIndex()],
problem,
......@@ -87,7 +87,7 @@ public:
}
// handle the boundary volume variables
for (const auto& scvFace : fvGeometry.scvfs())
for (const auto& scvFace : scvfs(fvGeometry))
{
// if we are not on a boundary, skip the rest
if (!scvFace.boundary())
......@@ -221,7 +221,7 @@ public:
// Update boundary volume variables
const auto& fvGeometry = problem_().model().fvGeometries(element);
for (const auto& scvFace : fvGeometry.scvfs())
for (const auto& scvFace : scvfs(fvGeometry))
{
// if we are not on a boundary, skip the rest
if (!scvFace.boundary())
......
......@@ -133,31 +133,44 @@ class FVElementGeometry
using ScvfIterator = Dumux::ScvfIterator<SubControlVolumeFace, std::vector<IndexType>, FVElementGeometryVector>;
public:
// This class in not default-constructible
FVElementGeometry() = delete;
// Constructor with vectors
FVElementGeometry(const FVElementGeometryVector& fvGeometryVector,
FVElementGeometry(const FVElementGeometryVector& localFvGeometry,
const std::vector<IndexType>& scvIndices,
const std::vector<IndexType>& scvfIndices)
: fvGeometryVector_(fvGeometryVector), scvIndices_(scvIndices), scvfIndices_(scvfIndices)
: localFvGeometry_(localFvGeometry),
scvIndices_(scvIndices),
scvfIndices_(scvfIndices)
{}
//! iterator range for sub control volumes
inline Dune::IteratorRange<ScvIterator> scvs() const
//! This is a free function found by means of ADL
//! To iterate over all sub control volumes of this FVElementGeometry use
//! for (const auto& scv : scvs(fvGeometry))
friend inline Dune::IteratorRange<ScvIterator>
scvs(const FVElementGeometry& g)
{
return Dune::IteratorRange<ScvIterator>(ScvIterator(scvIndices_.begin(), fvGeometryVector_),
ScvIterator(scvIndices_.end(), fvGeometryVector_));
return Dune::IteratorRange<ScvIterator>(ScvIterator(g.scvIndices().begin(), g.localFvGeometry()),
ScvIterator(g.scvIndices().end(), g.localFvGeometry()));
}
//! number of sub control volumes in this fv element geometry
std::size_t numScv() const
//! iterator range for sub control volume faces
//! This is a free function found by means of ADL
//! To iterate over all sub control volume faces of this FVElementGeometry use
//! for (const auto& scvf : scvfs(fvGeometry))
friend inline Dune::IteratorRange<ScvfIterator>
scvfs(const FVElementGeometry& g)
{
return scvIndices_.size();
return Dune::IteratorRange<ScvfIterator>(ScvfIterator(g.scvfIndices().begin(), g.localFvGeometry()),
ScvfIterator(g.scvfIndices().end(), g.localFvGeometry()));
}
//! iterator range for sub control volume faces
inline Dune::IteratorRange<ScvfIterator> scvfs() const
//! number of sub control volumes in this fv element geometry
std::size_t numScv() const
{
return Dune::IteratorRange<ScvfIterator>(ScvfIterator(scvfIndices_.begin(), fvGeometryVector_),
ScvfIterator(scvfIndices_.end(), fvGeometryVector_));
return scvIndices_.size();
}
//! number of sub control volumes in this fv element geometry
......@@ -167,7 +180,24 @@ public:
}
private:
const FVElementGeometryVector& fvGeometryVector_;
//! The sub control volume indices
//! Depending on the type of discretization and caching
//! these may be local or global indices
const std::vector<IndexType>& scvIndices() const
{ return scvIndices_; }
//! The sub control volume face indices
//! Depending on the type of discretization and caching
//! these may be local or global indices
const std::vector<IndexType>& scvfIndices() const
{ return scvfIndices_; }
//! The LocalFvGeometry object this FvElementGeometry belongs to
const FVElementGeometryVector& localFvGeometry() const
{ return localFvGeometry_; }
const FVElementGeometryVector& localFvGeometry_;
std::vector<IndexType> scvIndices_;
std::vector<IndexType> scvfIndices_;
};
......
......@@ -89,7 +89,7 @@ public:
hasNeumann_ = false;
hasOutflow_ = false;
for (auto&& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
int scvIdxLocal = scv.indexInElement();
(*this)[scvIdxLocal].reset();
......
......@@ -126,7 +126,7 @@ public:
this->model_().updatePVWeights(fvGeometry);
// calculation of the derivatives
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
// dof index and corresponding actual pri vars
const auto dofIdx = scv.dofIndex();
......@@ -264,7 +264,7 @@ protected:
// update the global stiffness matrix with the current partial derivatives
const auto& fvGeometry = this->model_().fvGeometries(element);
for (const auto& scvJ : fvGeometry.scvs())
for (const auto& scvJ : scvs(fvGeometry))
this->updateGlobalJacobian_(matrix, scvJ.dofIndex(), dofIdx, pvIdx, partialDeriv[scvJ.indexInElement()]);
}
......
......@@ -73,7 +73,7 @@ protected:
{
// calculate the mass flux over the scv faces and subtract
const auto& fvGeometry = this->fvGeometry_();
for (const auto& scvf : fvGeometry.scvfs())
for (const auto& scvf : scvfs(fvGeometry))
{
if (!scvf.boundary())
{
......@@ -187,8 +187,7 @@ protected:
const auto& fvGeometry = this->fvGeometry_();
if (this->bcTypes_().hasNeumann() || this->bcTypes_().hasOutflow())
{
for (const auto& scvf : fvGeometry.scvfs())
for (const auto& scvf : scvfs(fvGeometry))
{
if (scvf.boundary())
{
......@@ -201,7 +200,7 @@ protected:
// additionally treat mixed D/N conditions in a strong sense
if (this->bcTypes_().hasDirichlet())
{
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
BoundaryTypes bcTypes = this->bcTypes_(scv.indexInElement());
if (!bcTypes.hasDirichlet())
......
......@@ -87,12 +87,12 @@ public:
(*this)[0].reset();
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
if (!problem.model().onBoundary(scv))
return;
for (const auto& scvFace : fvGeometry.scvfs())
for (const auto& scvFace : scvfs(fvGeometry))
{
if (!scvFace.boundary())
continue;
......
......@@ -128,7 +128,7 @@ public:
// find the flux vars needed for the calculation of the flux into element
std::vector<IndexType> fluxVarIndices;
for (const auto& scvFaceJ : fvGeometry.scvfs())
for (const auto& scvFaceJ : scvfs(fvGeometry))
{
auto fluxVarsIdx = scvFaceJ.index();
......
......@@ -74,7 +74,7 @@ protected:
{
// calculate the mass flux over the scv faces
const auto& fvGeometry = this->fvGeometry_();
for (const auto& scvf : fvGeometry.scvfs())
for (const auto& scvf : scvfs(fvGeometry))
{
this->residual_[0] += this->asImp_().computeFlux_(scvf);
}
......@@ -93,7 +93,7 @@ protected:
{
const auto& fvGeometry = this->fvGeometry_();
for (const auto& scvf : fvGeometry.scvfs())
for (const auto& scvf : scvfs(fvGeometry))
{
if (scvf.boundary())
this->residual_[0] += evalBoundaryFluxes_(scvf);
......@@ -102,7 +102,7 @@ protected:
// additionally treat mixed D/N conditions in a strong sense
if (this->bcTypes_().hasDirichlet())
{
for (const auto& scvf : fvGeometry.scvfs())
for (const auto& scvf : scvfs(fvGeometry))
{
if (scvf.boundary())
this->asImp_().evalDirichlet_(scvf);
......
......@@ -292,7 +292,7 @@ protected:
// calculate the amount of conservation each quantity inside
// all sub control volumes
const auto& fvGeometry = fvGeometry_();
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
auto scvIdx = scv.indexInElement();
......@@ -305,7 +305,7 @@ protected:
{
PrimaryVariables source(0);
const auto& fvGeometry = fvGeometry_();
for (const auto& scv : fvGeometry)
for (const auto& scv : scvs(fvGeometry))
{
source += this->problem_().source(element_(), scv);
......@@ -327,7 +327,7 @@ protected:
{
// evaluate the volume terms (storage + source terms)
const auto& fvGeometry = fvGeometry_();
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
auto scvIdx = scv.indexInElement();
auto curExtrusionFactor = model_().curVolVars(scv).extrusionFactor();
......@@ -351,7 +351,7 @@ protected:
{
// evaluate the volume terms (storage + source terms)
const auto& fvGeometry = fvGeometry_();
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
auto scvIdx = scv.indexInElement();
auto prevExtrusionFactor = model_().prevVolVars(scv).extrusionFactor();
......
......@@ -862,7 +862,7 @@ protected:
const auto& fvGeometry = fvGeometries(element);
// loop over sub control volumes
for(const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
// let the problem do the dirty work of nailing down
// the initial solution.
......
......@@ -98,7 +98,7 @@ public:
this->curVolVars_().bindElement(element);
const auto& fvGeometry = this->fvGeometries(element);
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
const auto& spatialParams = this->problem_().spatialParams();
auto dofIdxGlobal = scv.dofIndex();
......
......@@ -162,7 +162,7 @@ public:
this->curVolVars_().bindElement(element);
const auto& fvGeometry = this->fvGeometries(element);
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
auto dofIdxGlobal = scv.dofIndex();
const auto& volVars = this->curVolVars(scv);
......
......@@ -148,7 +148,7 @@ public:
this->curVolVars_().bindElement(element);
const auto& fvGeometry = this->fvGeometries(element);
for (const auto& scv : fvGeometry.scvs())
for (const auto& scv : scvs(fvGeometry))
{
auto eIdx = scv.elementIndex();
auto dofIdxGlobal = scv.dofIndex();
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment