Commit 289b2b9a authored by Praetorius, Simon's avatar Praetorius, Simon
Browse files

working version of dune-functions assembling

parent 7668c6b7
#pragma once #pragma once
// std c++ headers // std c++ headers
#include <algorithm>
#include <cmath> #include <cmath>
#include <limits>
#include <string> #include <string>
#include <vector> #include <vector>
...@@ -82,7 +84,7 @@ namespace AMDiS ...@@ -82,7 +84,7 @@ namespace AMDiS
public: public:
/// Constructor. /// Constructor.
AdaptInfo(std::string name, int size = 1); explicit AdaptInfo(std::string name, int size = 1);
/// Destructor. /// Destructor.
virtual ~AdaptInfo() {} virtual ~AdaptInfo() {}
...@@ -427,7 +429,7 @@ namespace AMDiS ...@@ -427,7 +429,7 @@ namespace AMDiS
if (nTimesteps > 0) if (nTimesteps > 0)
return !(timestepNumber < nTimesteps); return !(timestepNumber < nTimesteps);
return !(std::abs(time - endTime) > DBL_TOL); return !(std::abs(time - endTime) > std::numeric_limits<double>::epsilon());
} }
......
...@@ -4,6 +4,8 @@ ...@@ -4,6 +4,8 @@
#include <dune/amdis/utility/TreePath.hpp> #include <dune/amdis/utility/TreePath.hpp>
#include <dune/amdis/utility/Visitor.hpp> #include <dune/amdis/utility/Visitor.hpp>
#include <dune/amdis/Math.hpp>
namespace AMDiS { namespace AMDiS {
template <class Traits> template <class Traits>
...@@ -65,7 +67,7 @@ void Assembler<Traits>::assemble( ...@@ -65,7 +67,7 @@ void Assembler<Traits>::assemble(
for (std::size_t i = 0; i < localView.size(); ++i) { for (std::size_t i = 0; i < localView.size(); ++i) {
auto const row = localIndexSet.index(i); auto const row = localIndexSet.index(i);
for (std::size_t j = 0; j < localView.size(); ++j) { for (std::size_t j = 0; j < localView.size(); ++j) {
if (elementMatrix(i,j) != 0.0) { if (std::abs(elementMatrix(i,j)) > threshold<double>) {
auto const col = localIndexSet.index(j); auto const col = localIndexSet.index(j);
matrix(row,col) += elementMatrix(i,j); matrix(row,col) += elementMatrix(i,j);
} }
...@@ -74,7 +76,7 @@ void Assembler<Traits>::assemble( ...@@ -74,7 +76,7 @@ void Assembler<Traits>::assemble(
// add element-vector to system-vector // add element-vector to system-vector
for (std::size_t i = 0; i < localView.size(); ++i) { for (std::size_t i = 0; i < localView.size(); ++i) {
if (elementVector[i] != 0.0) { if (std::abs(elementVector[i]) > threshold<double>) {
auto const idx = localIndexSet.index(i); auto const idx = localIndexSet.index(i);
rhs[idx] += elementVector[i]; rhs[idx] += elementVector[i];
} }
......
...@@ -2,6 +2,7 @@ ...@@ -2,6 +2,7 @@
// std c++ headers // std c++ headers
#include <map> #include <map>
#include <string>
// AMDiS includes // AMDiS includes
#include <dune/amdis/CreatorInterface.hpp> #include <dune/amdis/CreatorInterface.hpp>
......
#pragma once #pragma once
#include <functional> #include <functional>
#include <list>
#include <type_traits> #include <type_traits>
#include <vector> #include <vector>
......
#pragma once #pragma once
#include <string> #include <string>
//#include <vector>
//#include <array>
#include <memory> #include <memory>
#include <dune/functions/functionspacebases/lagrangebasis.hh> #include <dune/functions/functionspacebases/lagrangebasis.hh>
...@@ -80,7 +78,8 @@ namespace AMDiS ...@@ -80,7 +78,8 @@ namespace AMDiS
template <class W> template <class W>
void writeVertexData(Dune::TypeTree::LeafNodeTag, index_t<0>, W write) void writeVertexData(Dune::TypeTree::LeafNodeTag, index_t<0>, W write)
{ {
using namespace Dune::Functions::BasisBuilder; using Dune::Functions::BasisBuilder::makeBasis;
using Dune::Functions::BasisBuilder::lagrange;
auto fct = makeDiscreteFunction(basis_,treePath_,vector_); auto fct = makeDiscreteFunction(basis_,treePath_,vector_);
auto p1basis = makeBasis(basis_->gridView(), lagrange<1>()); auto p1basis = makeBasis(basis_->gridView(), lagrange<1>());
...@@ -97,7 +96,11 @@ namespace AMDiS ...@@ -97,7 +96,11 @@ namespace AMDiS
template <std::size_t C, class W> template <std::size_t C, class W>
void writeVertexData(Dune::TypeTree::PowerNodeTag, index_t<C>, W write) void writeVertexData(Dune::TypeTree::PowerNodeTag, index_t<C>, W write)
{ {
using namespace Dune::Functions::BasisBuilder; using Dune::Functions::BasisBuilder::makeBasis;
using Dune::Functions::BasisBuilder::lagrange;
using Dune::Functions::BasisBuilder::power;
using Dune::Functions::BasisBuilder::flatLexicographic;
assert( C == dow ); assert( C == dow );
auto fct = makeDiscreteFunction(basis_,treePath_,vector_); auto fct = makeDiscreteFunction(basis_,treePath_,vector_);
...@@ -116,78 +119,6 @@ namespace AMDiS ...@@ -116,78 +119,6 @@ namespace AMDiS
template <class NodeTag, std::size_t C, class W> template <class NodeTag, std::size_t C, class W>
void writeVertexData(NodeTag, index_t<C>, W) {} void writeVertexData(NodeTag, index_t<C>, W) {}
#if 0
/// default write method for time-depended data
template <class SystemVectorType>
void write(double time, SystemVectorType const& solutions)
{
vtkWriter->clear();
// copy dofvector to vertex data
forEach(range_<0, nComponents>, [this, &solutions](const auto _i)
{
this->dofVector2vertexVector(solutions, std::get<_i>(data_vectors));
vtkSeqWriter->addVertexData(std::get<_i>(data_vectors), names[_i]);
});
vtkSeqWriter->write(time/*, Dune::VTK::appendedraw*/);
}
/// default write method for stationary data
template <class SystemVectorType>
void write(SystemVectorType const& solutions)
{
vtkWriter->clear();
// copy dofvector to vertex data
forEach(range_<0, nComponents>, [this, &solutions](const auto _i)
{
this->dofVector2vertexVector(solutions, std::get<_i>(data_vectors));
vtkWriter->addVertexData(std::get<_i>(data_vectors), names[_i]);
});
vtkWriter->pwrite(filename, dir, "" /*, Dune::VTK::appendedraw*/);
}
template <class DOFVector, class Vector>
void dofVector2vertexVector(DOFVector const& dofvector, Vector& data)
{
using Geometry = typename MeshView::template Codim<0>::Geometry;
using RefElements = Dune::ReferenceElements<typename Geometry::ctype, Geometry::mydimension>;
data.resize(meshView.size(dim));
auto const& indexSet = meshView.indexSet();
auto const& feSpace = dofvector.getFeSpace();
auto localView = feSpace.localView();
auto localIndexSet = feSpace.localIndexSet();
// copy data to P1-vector
for (auto const& element : elements(meshView)) {
localView.bind(element);
localIndexSet.bind(localView);
auto const& localBasis = localView.tree().finiteElement().localBasis();
auto const& refElement = RefElements::general(element.type());
std::vector<Dune::FieldVector<double,1> > shapeValues;
std::size_t nVertices = element.subEntities(dim);
for (std::size_t i = 0; i < nVertices; ++i) {
auto const& v = element.template subEntity<dim>(i);
auto pos = refElement.position(i, dim);
localBasis.evaluateFunction(pos, shapeValues);
std::size_t idx = indexSet.index(v);
data[idx] = 0.0;
for (std::size_t j = 0; j < shapeValues.size(); ++j) {
const auto global_idx = localIndexSet.index(j);
data[idx] += dofvector[global_idx] * shapeValues[j];
}
}
}
}
#endif
private: private:
std::shared_ptr<GlobalBasis> basis_; std::shared_ptr<GlobalBasis> basis_;
TreePath treePath_; TreePath treePath_;
......
...@@ -39,7 +39,7 @@ namespace AMDiS ...@@ -39,7 +39,7 @@ namespace AMDiS
using Element = typename GridView::template Codim<0>::Entity; using Element = typename GridView::template Codim<0>::Entity;
public: public:
FiniteElementSpaces(std::shared_ptr<FeSpaces> const& feSpaces) explicit FiniteElementSpaces(std::shared_ptr<FeSpaces> const& feSpaces)
: feSpaces_(feSpaces) : feSpaces_(feSpaces)
, localViews_(mapTuple([](auto const& basis) { return basis.localView(); }, *feSpaces)) , localViews_(mapTuple([](auto const& basis) { return basis.localView(); }, *feSpaces))
, localIndexSets_(mapTuple([](auto const& basis) { return basis.localIndexSet(); }, *feSpaces)) , localIndexSets_(mapTuple([](auto const& basis) { return basis.localIndexSet(); }, *feSpaces))
......
#pragma once #pragma once
#include <cstdint>
namespace AMDiS namespace AMDiS
{ {
/** \ingroup Common /** \ingroup Common
...@@ -15,7 +17,7 @@ namespace AMDiS ...@@ -15,7 +17,7 @@ namespace AMDiS
constexpr Flag() = default; constexpr Flag() = default;
/// Constructs a Flag initialized by f /// Constructs a Flag initialized by f
constexpr Flag(const unsigned long f) constexpr Flag(const std::uint64_t f)
: flags(f) : flags(f)
{} {}
...@@ -52,7 +54,7 @@ namespace AMDiS ...@@ -52,7 +54,7 @@ namespace AMDiS
} }
/// Set \ref flags /// Set \ref flags
constexpr void setFlags(const unsigned long f) constexpr void setFlags(const std::uint64_t f)
{ {
flags = f; flags = f;
} }
...@@ -64,7 +66,7 @@ namespace AMDiS ...@@ -64,7 +66,7 @@ namespace AMDiS
} }
/// Sets \ref flags to \ref flags | f /// Sets \ref flags to \ref flags | f
constexpr void setFlag(const unsigned long f) constexpr void setFlag(const std::uint64_t f)
{ {
flags |= f; flags |= f;
} }
...@@ -76,7 +78,7 @@ namespace AMDiS ...@@ -76,7 +78,7 @@ namespace AMDiS
} }
/// Sets \ref flags to \ref flags & ~f /// Sets \ref flags to \ref flags & ~f
constexpr void unsetFlag(const unsigned long f) constexpr void unsetFlag(const std::uint64_t f)
{ {
flags &= ~f; flags &= ~f;
} }
...@@ -87,7 +89,7 @@ namespace AMDiS ...@@ -87,7 +89,7 @@ namespace AMDiS
flags &= ~f.flags; flags &= ~f.flags;
} }
constexpr unsigned long getFlags() const constexpr std::uint64_t getFlags() const
{ {
return flags; return flags;
} }
...@@ -170,7 +172,7 @@ namespace AMDiS ...@@ -170,7 +172,7 @@ namespace AMDiS
protected: protected:
/// Internal flag representation /// Internal flag representation
unsigned long flags = 0; std::uint64_t flags = 0;
}; };
} // end namespace AMDiS } // end namespace AMDiS
...@@ -56,8 +56,8 @@ namespace AMDiS ...@@ -56,8 +56,8 @@ namespace AMDiS
test_exit(file_exists(fn), test_exit(file_exists(fn),
"init-file '", fn, "' cannot be opened for reading"); "init-file '", fn, "' cannot be opened for reading");
using namespace boost::property_tree; using boost::property_tree::json_parser::read_json;
json_parser::read_json(fn, pt); read_json(fn, pt);
} }
......
...@@ -265,7 +265,7 @@ namespace AMDiS ...@@ -265,7 +265,7 @@ namespace AMDiS
/// save singlett-data to file with filename fn /// save singlett-data to file with filename fn
static void save(std::string /*fn*/) static void save(std::string /*fn*/)
{ {
using namespace boost::property_tree; // using boost::property_tree::json_parser;
// json_parser::write_jason(fn, singlett().pt); // json_parser::write_jason(fn, singlett().pt);
} }
......
...@@ -23,7 +23,7 @@ namespace AMDiS ...@@ -23,7 +23,7 @@ namespace AMDiS
using LocalGeometry = typename Impl::Get<LocalContext>::Geometry; using LocalGeometry = typename Impl::Get<LocalContext>::Geometry;
public: public:
LocalAssembler(int degree, FirstOrderType type = GRD_PHI) explicit LocalAssembler(int degree, FirstOrderType type = GRD_PHI)
: degree_(degree) : degree_(degree)
, type_(type) , type_(type)
{} {}
......
#pragma once #pragma once
#include <algorithm>
#include <cmath>
#include <cstdint>
#include <limits>
#include <string> #include <string>
#include <type_traits> #include <type_traits>
#include <cmath>
#include <cfloat>
namespace AMDiS namespace AMDiS
{ {
...@@ -101,8 +103,12 @@ namespace AMDiS ...@@ -101,8 +103,12 @@ namespace AMDiS
s = ""; s = "";
} }
template <class T>
constexpr T threshold = T(1.e-16); //Math::sqr(std::numeric_limits<T>::epsilon());
/// Calculates factorial of i /// Calculates factorial of i
constexpr unsigned long factorial(unsigned long i) constexpr std::uint64_t factorial(std::uint64_t i)
{ {
return i <= 1 ? 1 : i * factorial(i - 1); return i <= 1 ? 1 : i * factorial(i - 1);
} }
...@@ -128,8 +134,4 @@ namespace AMDiS ...@@ -128,8 +134,4 @@ namespace AMDiS
constexpr double m_sqrt2 = 1.41421356237309504880; constexpr double m_sqrt2 = 1.41421356237309504880;
constexpr double m_sqrt1_2 = 0.70710678118654752440; constexpr double m_sqrt1_2 = 0.70710678118654752440;
// tolerance for floating point comparison
#define DBL_TOL DBL_EPSILON
#define FLT_TOL FLT_EPSILON
} // end namespace AMDiS } // end namespace AMDiS
#pragma once #pragma once
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include <array> #include <array>
#include <memory> #include <memory>
#include <string>
#include <dune/common/filledarray.hh> #include <dune/common/filledarray.hh>
#include <dune/common/fvector.hh> #include <dune/common/fvector.hh>
......
...@@ -134,10 +134,28 @@ namespace AMDiS ...@@ -134,10 +134,28 @@ namespace AMDiS
{ {
element_ = &element; element_ = &element;
geometry_ = &geometry; geometry_ = &geometry;
for (auto* operatorTerm : zeroOrder)
operatorTerm->bind(element);
for (auto* operatorTerm : firstOrderGrdPhi)
operatorTerm->bind(element);
for (auto* operatorTerm : firstOrderGrdPsi)
operatorTerm->bind(element);
for (auto* operatorTerm : secondOrder)
operatorTerm->bind(element);
} }
void unbind() void unbind()
{ {
for (auto* operatorTerm : zeroOrder)
operatorTerm->unbind();
for (auto* operatorTerm : firstOrderGrdPhi)
operatorTerm->unbind();
for (auto* operatorTerm : firstOrderGrdPsi)
operatorTerm->unbind();
for (auto* operatorTerm : secondOrder)
operatorTerm->unbind();
element_ = nullptr; element_ = nullptr;
geometry_ = nullptr; geometry_ = nullptr;
} }
......
#pragma once #pragma once
#include <algorithm>
#include <list>
namespace AMDiS { namespace AMDiS {
template <class GridView, class LocalContext> template <class GridView, class LocalContext>
...@@ -45,7 +48,7 @@ getQuadratureDegree(Dune::GeometryType t, LocalGeometry const& geometry, int ord ...@@ -45,7 +48,7 @@ getQuadratureDegree(Dune::GeometryType t, LocalGeometry const& geometry, int ord
int maxTermDegree = 0; int maxTermDegree = 0;
for (OperatorTermType* term : *terms) for (OperatorTermType* term : *terms)
maxTermDegree = std::max(maxTermDegree, term->getDegree(t)); maxTermDegree = std::max(maxTermDegree, term->getDegree());
int degree = psiDegree_ + phiDegree_ + maxTermDegree; int degree = psiDegree_ + phiDegree_ + maxTermDegree;
if (t.isSimplex()) if (t.isSimplex())
......
#pragma once #pragma once
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include <vector> #include <vector>
#include <type_traits> #include <type_traits>
...@@ -24,8 +20,12 @@ namespace AMDiS ...@@ -24,8 +20,12 @@ namespace AMDiS
static constexpr int dow = LocalContext::Geometry::coorddimension; static constexpr int dow = LocalContext::Geometry::coorddimension;
using QuadratureRule = QuadratureRuleFactory_t<LocalContext,double,dim>; using QuadratureRule = QuadratureRuleFactory_t<LocalContext,double,dim>;
using Element = typename Impl::Get<LocalContext>::Entity;
public: public:
virtual void bind(Element const& element) = 0;
virtual void unbind() = 0;
// initialize operator-term on the current element // initialize operator-term on the current element
virtual void init(LocalContext const& element, QuadratureRule const& points) = 0; virtual void init(LocalContext const& element, QuadratureRule const& points) = 0;
...@@ -62,7 +62,7 @@ namespace AMDiS ...@@ -62,7 +62,7 @@ namespace AMDiS
// return the polynomial degree, necessary to intergrate the operator-term // return the polynomial degree, necessary to intergrate the operator-term
// on an element accurately // on an element accurately
virtual int getDegree(Dune::GeometryType const& t) const = 0; virtual int getDegree() const = 0;
}; };
...@@ -83,16 +83,24 @@ namespace AMDiS ...@@ -83,16 +83,24 @@ namespace AMDiS
{ {
using Super = OperatorTerm<LocalContext>; using Super = OperatorTerm<LocalContext>;
using QuadratureRule = typename Super::QuadratureRule; using QuadratureRule = typename Super::QuadratureRule;
using Element = typename Super::Element;
static constexpr int dow = Super::dow; static constexpr int dow = Super::dow;
public: public:
/// Constructor, stores a copy of the expression `expr` and of the traits `traits`. /// Constructor, stores a copy of the expression `expr` and of the traits `traits`.
GenericOperatorTerm(Expression const& expr, Traits traits = {}) explicit GenericOperatorTerm(Expression const& expr, Traits traits = {})
: expr(expr) : expr(expr)
, traits(traits) , traits(traits)
{} {}
virtual void bind(Element const& element) final
{
expr.bind(element);
}
virtual void unbind() final {}
/// \brief Initialize the expression on the current (inside-)element, in the quadrature points. /// \brief Initialize the expression on the current (inside-)element, in the quadrature points.
/** /**
* This initialization does not only bind the operator-term to the inside-element, * This initialization does not only bind the operator-term to the inside-element,
...@@ -102,21 +110,21 @@ namespace AMDiS ...@@ -102,21 +110,21 @@ namespace AMDiS
* Note: For entities the expression is bound to the `element` directly, but * Note: For entities the expression is bound to the `element` directly, but
* for intersections, the expression is bound to inside-entity of the element. * for intersections, the expression is bound to inside-entity of the element.
**/ **/
virtual void init(LocalContext const& element, QuadratureRule const& points) override virtual void init(LocalContext const& element, QuadratureRule const& points) final
{ {
expr.init(get_entity(element), points); expr.init(get_entity(element), points);
} }
/// Calculates `expr[iq] * test * trial` /// Calculates `expr[iq] * test * trial`
virtual double eval(