Commit 90c3d73b authored by Praetorius, Simon's avatar Praetorius, Simon
Browse files

improved error messages, added quadrature degree parameter

parent e4baaf0f
...@@ -3,7 +3,8 @@ ...@@ -3,7 +3,8 @@
#include <cassert> #include <cassert>
#include <type_traits> #include <type_traits>
#include <dune/amdis/gridfunctions/GridFunctionConcepts.hpp> #include <dune/amdis/GridFunctions.hpp>
#include <dune/amdis/common/Utility.hpp>
#include <dune/amdis/utility/GetDegree.hpp> #include <dune/amdis/utility/GetDegree.hpp>
namespace AMDiS namespace AMDiS
...@@ -24,10 +25,11 @@ namespace AMDiS ...@@ -24,10 +25,11 @@ namespace AMDiS
* \ref ExpressionBase, and stores a copy. Additionally, it gets the * \ref ExpressionBase, and stores a copy. Additionally, it gets the
* differentiation order, to calculate the quadrature degree in \ref getDegree. * differentiation order, to calculate the quadrature degree in \ref getDegree.
**/ **/
GridFunctionOperatorBase(GridFunction const& gridFct, int order) GridFunctionOperatorBase(GridFunction const& gridFct, int order, int degree = -1)
: gridFct_(gridFct) : gridFct_(gridFct)
, localFct_(localFunction(gridFct_)) , localFct_(localFunction(gridFct_))
, order_(order) , order_(order)
, degree_(degree)
{} {}
/// \brief Binds operator to `element` and `geometry`. /// \brief Binds operator to `element` and `geometry`.
...@@ -75,7 +77,7 @@ namespace AMDiS ...@@ -75,7 +77,7 @@ namespace AMDiS
assert( bound_ ); assert( bound_ );
int psiDegree = getPolynomialDegree(node); int psiDegree = getPolynomialDegree(node);
int coeffDegree = order(localFct_); int coeffDegree = getGridFctDegree(localFct_);
int degree = psiDegree + coeffDegree; int degree = psiDegree + coeffDegree;
if (isSimplex_) if (isSimplex_)
...@@ -100,7 +102,7 @@ namespace AMDiS ...@@ -100,7 +102,7 @@ namespace AMDiS
int psiDegree = getPolynomialDegree(rowNode); int psiDegree = getPolynomialDegree(rowNode);
int phiDegree = getPolynomialDegree(colNode); int phiDegree = getPolynomialDegree(colNode);
int coeffDegree = order(localFct_); int coeffDegree = getGridFctDegree(localFct_);
int degree = psiDegree + phiDegree + coeffDegree; int degree = psiDegree + phiDegree + coeffDegree;
if (isSimplex_) if (isSimplex_)
...@@ -111,11 +113,27 @@ namespace AMDiS ...@@ -111,11 +113,27 @@ namespace AMDiS
return degree; return degree;
} }
protected:
template <class LocalFct,
REQUIRES(Concepts::HasOrder<LocalFct>)>
int getGridFctDegree(LocalFct const& localFct) const
{
return degree_ >= 0 ? degree_ : order(localFct_);
}
template <class LocalFct,
REQUIRES(not Concepts::HasOrder<LocalFct>)>
int getGridFctDegree(LocalFct const& localFct) const
{
return degree_;
}
private: private:
GridFunction gridFct_; GridFunction gridFct_;
LocalFunction localFct_; LocalFunction localFct_;
int order_; //< the derivative order of this operator int order_; //< the derivative order of this operator
int degree_; //< the polynomial order of the gridFunction
bool isSimplex_ = false; //< the bound element is a simplex bool isSimplex_ = false; //< the bound element is a simplex
bool isAffine_ = false; //< the bound geometry is affine bool isAffine_ = false; //< the bound geometry is affine
...@@ -166,50 +184,84 @@ namespace AMDiS ...@@ -166,50 +184,84 @@ namespace AMDiS
} }
}; };
namespace Concepts
{
namespace Definition
{
struct HasGridFunctionOrder
{
template <class F, class GridView>
auto requires_(F&& f, GridView const& gridView)
-> decltype( order(localFunction(makeGridFunction(f, gridView))) );
};
}
template <class F, class GridView = Dune::YaspGrid<2>::LeafGridView>
constexpr bool HasGridFunctionOrder = models<Definition::HasGridFunctionOrder(F, GridView)>;
} // end namespace Concepts
template <class Tag, class Expr> template <class Tag, class Expr>
struct ExpressionPreOperator struct ExpressionPreOperator
{ {
Tag tag; Tag tag;
Expr expr; Expr expr;
int order = -1;
}; };
/// Store tag and expression in struct /// Store tag and expression in struct
template <class Tag, class Expr> template <class Tag, class Expr>
auto makeOperator(Tag t, Expr const& expr) auto makeOperator(Tag t, Expr const& expr)
{ {
using RawExpr = Underlying_t<Expr>;
static_assert(Concepts::HasGridFunctionOrder<RawExpr>,
"Polynomial degree of expression can not be deduced. You need to provide an explicit value for polynomial order in `makeOperator()`.");
return ExpressionPreOperator<Tag, Expr>{t, expr}; return ExpressionPreOperator<Tag, Expr>{t, expr};
} }
template <class Tag, class Expr>
auto makeOperator(Tag t, Expr const& expr, int order)
{
return ExpressionPreOperator<Tag, Expr>{t, expr, order};
}
/// Generate an \ref GridFunctionOperator from a PreOperator (tag, expr). /// Generate an \ref GridFunctionOperator from a PreOperator (tag, expr).
/// @{
template <class Tag, class Expr, class GridView> template <class Tag, class Expr, class GridView>
auto makeGridOperator(ExpressionPreOperator<Tag, Expr> const& op, GridView const& gridView) auto makeGridOperator(ExpressionPreOperator<Tag, Expr> const& op, GridView const& gridView)
{ {
auto gridFct = makeGridFunction(op.expr, gridView, Dune::PriorityTag<42>{}); auto gridFct = makeGridFunction(op.expr, gridView);
return GridFunctionOperator<Tag, decltype(gridFct)>{op.tag, gridFct}; return GridFunctionOperator<Tag, decltype(gridFct)>{op.tag, gridFct, op.order};
} }
template <class Tag, class Expr, class GridView> template <class Tag, class Expr, class GridView>
auto makeGridOperator(std::reference_wrapper<ExpressionPreOperator<Tag, Expr>> op, GridView const& gridView) auto makeGridOperator(std::reference_wrapper<ExpressionPreOperator<Tag, Expr>> op, GridView const& gridView)
{ {
ExpressionPreOperator<Tag, Expr> const& op_ref = op; ExpressionPreOperator<Tag, Expr> const& op_ref = op;
auto gridFct = makeGridFunction(std::ref(op_ref.expr), gridView, Dune::PriorityTag<42>{}); auto gridFct = makeGridFunction(std::ref(op_ref.expr), gridView);
return GridFunctionOperator<Tag, decltype(gridFct)>{op_ref.tag, gridFct}; return GridFunctionOperator<Tag, decltype(gridFct)>{op_ref.tag, gridFct, op_ref.order};
} }
/// @}
/// Generate a shared_ptr to \ref GridFunctionOperator from a PreOperator (tag, expr). /// Generate a shared_ptr to \ref GridFunctionOperator from a PreOperator (tag, expr).
/// @{
template <class Tag, class Expr, class GridView> template <class Tag, class Expr, class GridView>
auto makeGridOperatorPtr(ExpressionPreOperator<Tag, Expr> const& op, GridView const& gridView) auto makeGridOperatorPtr(ExpressionPreOperator<Tag, Expr> const& op, GridView const& gridView)
{ {
auto gridFct = makeGridFunction(op.expr, gridView, Dune::PriorityTag<42>{}); auto gridFct = makeGridFunction(op.expr, gridView);
return std::make_shared<GridFunctionOperator<Tag, decltype(gridFct)>>(op.tag, gridFct); return std::make_shared<GridFunctionOperator<Tag, decltype(gridFct)>>(op.tag, gridFct, op.order);
} }
template <class Tag, class Expr, class GridView> template <class Tag, class Expr, class GridView>
auto makeGridOperatorPtr(std::reference_wrapper<ExpressionPreOperator<Tag, Expr>> op, GridView const& gridView) auto makeGridOperatorPtr(std::reference_wrapper<ExpressionPreOperator<Tag, Expr>> op, GridView const& gridView)
{ {
ExpressionPreOperator<Tag, Expr> const& op_ref = op; ExpressionPreOperator<Tag, Expr> const& op_ref = op;
auto gridFct = makeGridFunction(std::ref(op_ref.expr), gridView, Dune::PriorityTag<42>{}); auto gridFct = makeGridFunction(std::ref(op_ref.expr), gridView);
return std::make_shared<GridFunctionOperator<Tag, decltype(gridFct)>>(op_ref.tag, gridFct); return std::make_shared<GridFunctionOperator<Tag, decltype(gridFct)>>(op_ref.tag, gridFct, op_ref.order);
} }
/// @}
} // end namespace AMDiS } // end namespace AMDiS
...@@ -6,3 +6,14 @@ ...@@ -6,3 +6,14 @@
#include <dune/amdis/gridfunctions/DerivativeGridFunction.hpp> #include <dune/amdis/gridfunctions/DerivativeGridFunction.hpp>
#include <dune/amdis/gridfunctions/FunctorGridFunction.hpp> #include <dune/amdis/gridfunctions/FunctorGridFunction.hpp>
#include <dune/amdis/gridfunctions/OperationsGridFunction.hpp> #include <dune/amdis/gridfunctions/OperationsGridFunction.hpp>
namespace AMDiS
{
// Generator for Gridfunctions from Pre-Gridfunctions
template <class PreGridFct, class GridView>
decltype(auto) makeGridFunction(PreGridFct&& preGridFct, GridView const& gridView)
{
return Impl::makeGridFunctionImpl(std::forward<PreGridFct>(preGridFct), gridView, Dune::PriorityTag<10>{});
}
} // end namespace AMDiS
...@@ -31,6 +31,7 @@ ...@@ -31,6 +31,7 @@
#include <dune/amdis/common/TypeDefs.hpp> #include <dune/amdis/common/TypeDefs.hpp>
#include <dune/amdis/common/Utility.hpp> #include <dune/amdis/common/Utility.hpp>
#include <dune/amdis/GridFunctions.hpp>
#include <dune/amdis/gridfunctions/DOFVectorView.hpp> #include <dune/amdis/gridfunctions/DOFVectorView.hpp>
#include <dune/amdis/io/FileWriterInterface.hpp> #include <dune/amdis/io/FileWriterInterface.hpp>
......
...@@ -216,7 +216,7 @@ addDirichletBC(Predicate const& predicate, RowTreePath row, ColTreePath col, Val ...@@ -216,7 +216,7 @@ addDirichletBC(Predicate const& predicate, RowTreePath row, ColTreePath col, Val
auto i = child(globalBasis->localView().tree(), makeTreePath(row)); auto i = child(globalBasis->localView().tree(), makeTreePath(row));
auto j = child(globalBasis->localView().tree(), makeTreePath(col)); auto j = child(globalBasis->localView().tree(), makeTreePath(col));
auto valueGridFct = makeGridFunction(values, globalBasis->gridView(), Dune::PriorityTag<42>{}); auto valueGridFct = makeGridFunction(values, globalBasis->gridView());
using Range = typename decltype(valueGridFct)::Range; using Range = typename decltype(valueGridFct)::Range;
using BcType = DirichletBC<WorldVector,Range>; using BcType = DirichletBC<WorldVector,Range>;
......
...@@ -20,8 +20,8 @@ namespace AMDiS ...@@ -20,8 +20,8 @@ namespace AMDiS
using Transposed = GridFunctionOperator<tag::test_divtrialvec, GridFct>; using Transposed = GridFunctionOperator<tag::test_divtrialvec, GridFct>;
public: public:
GridFunctionOperator(tag::divtestvec_trial, GridFct const& expr) GridFunctionOperator(tag::divtestvec_trial, GridFct const& expr, int degree)
: Transposed(tag::test_divtrialvec{}, expr) : Transposed(tag::test_divtrialvec{}, expr, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -20,8 +20,8 @@ namespace AMDiS ...@@ -20,8 +20,8 @@ namespace AMDiS
using Transposed = GridFunctionOperator<tag::test_gradtrial, GridFct>; using Transposed = GridFunctionOperator<tag::test_gradtrial, GridFct>;
public: public:
GridFunctionOperator(tag::gradtest_trial, GridFct const& expr) GridFunctionOperator(tag::gradtest_trial, GridFct const& expr, int degree)
: Transposed(tag::test_gradtrial{}, expr) : Transposed(tag::test_gradtrial{}, expr, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -20,8 +20,8 @@ namespace AMDiS ...@@ -20,8 +20,8 @@ namespace AMDiS
using Transposed = GridFunctionOperator<tag::testvec_gradtrial, GridFct>; using Transposed = GridFunctionOperator<tag::testvec_gradtrial, GridFct>;
public: public:
GridFunctionOperator(tag::gradtest_trialvec, GridFct const& expr) GridFunctionOperator(tag::gradtest_trialvec, GridFct const& expr, int degree)
: Transposed(tag::testvec_gradtrial{}, expr) : Transposed(tag::testvec_gradtrial{}, expr, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -23,8 +23,8 @@ namespace AMDiS ...@@ -23,8 +23,8 @@ namespace AMDiS
using Transposed = GridFunctionOperator<tag::test_partialtrial, GridFct>; using Transposed = GridFunctionOperator<tag::test_partialtrial, GridFct>;
public: public:
GridFunctionOperator(tag::partialtest_trial tag, GridFct const& expr) GridFunctionOperator(tag::partialtest_trial tag, GridFct const& expr, int degree)
: Transposed(tag::test_partialtrial{tag.comp}, expr) : Transposed(tag::test_partialtrial{tag.comp}, expr, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -24,8 +24,8 @@ namespace AMDiS ...@@ -24,8 +24,8 @@ namespace AMDiS
static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." ); static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." );
public: public:
GridFunctionOperator(tag::test_divtrialvec, GridFct const& expr) GridFunctionOperator(tag::test_divtrialvec, GridFct const& expr, int degree)
: Super(expr, 1) : Super(expr, 1, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -24,8 +24,8 @@ namespace AMDiS ...@@ -24,8 +24,8 @@ namespace AMDiS
static_assert( Category::Vector<typename GridFct::Range>, "Expression must be of vector type." ); static_assert( Category::Vector<typename GridFct::Range>, "Expression must be of vector type." );
public: public:
GridFunctionOperator(tag::test_gradtrial, GridFct const& expr) GridFunctionOperator(tag::test_gradtrial, GridFct const& expr, int degree)
: Super(expr, 1) : Super(expr, 1, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -27,8 +27,8 @@ namespace AMDiS ...@@ -27,8 +27,8 @@ namespace AMDiS
static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." ); static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." );
public: public:
GridFunctionOperator(tag::test_partialtrial tag, GridFct const& expr) GridFunctionOperator(tag::test_partialtrial tag, GridFct const& expr, int degree)
: Super(expr, 1) : Super(expr, 1, degree)
, comp_(tag.comp) , comp_(tag.comp)
{} {}
......
...@@ -24,8 +24,8 @@ namespace AMDiS ...@@ -24,8 +24,8 @@ namespace AMDiS
static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." ); static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." );
public: public:
GridFunctionOperator(tag::testvec_gradtrial, GridFct const& expr) GridFunctionOperator(tag::testvec_gradtrial, GridFct const& expr, int degree)
: Super(expr, 1) : Super(expr, 1, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -24,8 +24,8 @@ namespace AMDiS ...@@ -24,8 +24,8 @@ namespace AMDiS
static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." ); static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." );
public: public:
GridFunctionOperator(tag::divtestvec_divtrialvec, GridFct const& expr) GridFunctionOperator(tag::divtestvec_divtrialvec, GridFct const& expr, int degree)
: Super(expr, 2) : Super(expr, 2, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -26,8 +26,8 @@ namespace AMDiS ...@@ -26,8 +26,8 @@ namespace AMDiS
"Expression must be of scalar or matrix type." ); "Expression must be of scalar or matrix type." );
public: public:
GridFunctionOperator(tag::gradtest_gradtrial, GridFct const& expr) GridFunctionOperator(tag::gradtest_gradtrial, GridFct const& expr, int degree)
: Super(expr, 2) : Super(expr, 2, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -28,8 +28,8 @@ namespace AMDiS ...@@ -28,8 +28,8 @@ namespace AMDiS
static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." ); static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." );
public: public:
GridFunctionOperator(tag::partialtest_partialtrial tag, GridFct const& expr) GridFunctionOperator(tag::partialtest_partialtrial tag, GridFct const& expr, int degree)
: Super(expr, 2) : Super(expr, 2, degree)
, compTest_(tag.comp_test) , compTest_(tag.comp_test)
, compTrial_(tag.comp_trial) , compTrial_(tag.comp_trial)
{} {}
......
...@@ -23,8 +23,8 @@ namespace AMDiS ...@@ -23,8 +23,8 @@ namespace AMDiS
static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." ); static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." );
public: public:
GridFunctionOperator(tag::test, GridFct const& expr) GridFunctionOperator(tag::test, GridFct const& expr, int degree)
: Super(expr, 0) : Super(expr, 0, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -23,8 +23,8 @@ namespace AMDiS ...@@ -23,8 +23,8 @@ namespace AMDiS
static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." ); static_assert( Category::Scalar<typename GridFct::Range>, "Expression must be of scalar type." );
public: public:
GridFunctionOperator(tag::test_trial, GridFct const& expr) GridFunctionOperator(tag::test_trial, GridFct const& expr, int degree)
: Super(expr, 0) : Super(expr, 0, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -23,8 +23,8 @@ namespace AMDiS ...@@ -23,8 +23,8 @@ namespace AMDiS
static_assert( Category::Vector<typename GridFct::Range>, "Expression must be of vector type." ); static_assert( Category::Vector<typename GridFct::Range>, "Expression must be of vector type." );
public: public:
GridFunctionOperator(tag::test_trialvec, GridFct const& expr) GridFunctionOperator(tag::test_trialvec, GridFct const& expr, int degree)
: Super(expr, 0) : Super(expr, 0, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -23,8 +23,8 @@ namespace AMDiS ...@@ -23,8 +23,8 @@ namespace AMDiS
static_assert( Category::Vector<typename GridFct::Range>, "Expression must be of vector type." ); static_assert( Category::Vector<typename GridFct::Range>, "Expression must be of vector type." );
public: public:
GridFunctionOperator(tag::testvec, GridFct const& expr) GridFunctionOperator(tag::testvec, GridFct const& expr, int degree)
: Super(expr, 0) : Super(expr, 0, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
...@@ -20,8 +20,8 @@ namespace AMDiS ...@@ -20,8 +20,8 @@ namespace AMDiS
using Transposed = GridFunctionOperator<tag::test_trialvec, GridFct>; using Transposed = GridFunctionOperator<tag::test_trialvec, GridFct>;
public: public:
GridFunctionOperator(tag::testvec_trial, GridFct const& expr) GridFunctionOperator(tag::testvec_trial, GridFct const& expr, int degree)
: Transposed(tag::test_trialvec{}, expr) : Transposed(tag::test_trialvec{}, expr, degree)
{} {}
template <class Context, class QuadratureRule, template <class Context, class QuadratureRule,
......
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