From 15764e96beb2e69deb4c9a1e7fef6a79816e5e08 Mon Sep 17 00:00:00 2001
From: Simon Praetorius <simon.praetorius@tu-dresden.de>
Date: Mon, 2 Jul 2018 15:32:33 +0200
Subject: [PATCH] Derivative Gridfunction corrected

---
 src/amdis/Assembler.hpp                         |  2 +-
 src/amdis/ProblemStat.hpp                       |  1 +
 src/amdis/common/TupleUtility.hpp               |  4 ++--
 .../gridfunctions/AnalyticGridFunction.hpp      |  4 ++++
 .../gridfunctions/ConstantGridFunction.hpp      |  4 ++++
 src/amdis/gridfunctions/DOFVectorView.hpp       |  5 +++++
 .../gridfunctions/DerivativeGridFunction.hpp    | 17 ++++++-----------
 src/amdis/gridfunctions/FunctorGridFunction.hpp |  9 ++++++---
 test/TupleUtilityTest.cpp                       |  8 ++++----
 9 files changed, 33 insertions(+), 21 deletions(-)

diff --git a/src/amdis/Assembler.hpp b/src/amdis/Assembler.hpp
index be425fc9..8473ac32 100644
--- a/src/amdis/Assembler.hpp
+++ b/src/amdis/Assembler.hpp
@@ -8,7 +8,7 @@
 
 #include <amdis/DirichletBC.hpp>
 #include <amdis/LinearAlgebra.hpp>
-#include <amdis/LocalAssemblerBase.hpp>
+#include <amdis/LocalAssemblerList.hpp>
 #include <amdis/common/Mpl.hpp>
 #include <amdis/common/TypeDefs.hpp>
 
diff --git a/src/amdis/ProblemStat.hpp b/src/amdis/ProblemStat.hpp
index 9352089e..47e5a636 100644
--- a/src/amdis/ProblemStat.hpp
+++ b/src/amdis/ProblemStat.hpp
@@ -19,6 +19,7 @@
 #include <amdis/Flag.hpp>
 #include <amdis/Initfile.hpp>
 #include <amdis/LinearAlgebra.hpp>
+#include <amdis/LocalAssemblerList.hpp>
 #include <amdis/Marker.hpp>
 #include <amdis/Mesh.hpp>
 #include <amdis/ProblemStatBase.hpp>
diff --git a/src/amdis/common/TupleUtility.hpp b/src/amdis/common/TupleUtility.hpp
index 202622fd..0a6f1c03 100644
--- a/src/amdis/common/TupleUtility.hpp
+++ b/src/amdis/common/TupleUtility.hpp
@@ -31,7 +31,7 @@ namespace AMDiS
       {
         static_assert(std::tuple_size<Tuple>::value == sizeof...(args),
             "Nr. of argument != tuple-size");
-        return {std::forward<Args>(args)...};
+        return Tuple{std::forward<Args>(args)...};
       }
     };
 
@@ -43,7 +43,7 @@ namespace AMDiS
       {
         static_assert(std::tuple_size<Tuple>::value == 0,
             "Construction of empty tuples with empty argument list only!");
-        return {};
+        return Tuple{};
       }
     };
 
diff --git a/src/amdis/gridfunctions/AnalyticGridFunction.hpp b/src/amdis/gridfunctions/AnalyticGridFunction.hpp
index 40bd3918..c40e5af1 100644
--- a/src/amdis/gridfunctions/AnalyticGridFunction.hpp
+++ b/src/amdis/gridfunctions/AnalyticGridFunction.hpp
@@ -25,6 +25,8 @@ namespace AMDiS
 
     using Geometry = typename LocalContext::Geometry;
 
+    enum { hasDerivative = true };
+
   public:
     AnalyticLocalFunction(Function const& fct)
       : fct_{fct}
@@ -100,6 +102,8 @@ namespace AMDiS
     using Domain = typename EntitySet::GlobalCoordinate;
     using Range = std::decay_t<std::result_of_t<Function(Domain)>>;
 
+    enum { hasDerivative = true };
+
   private:
     using Element = typename EntitySet::Element;
     using LocalDomain = typename EntitySet::LocalCoordinate;
diff --git a/src/amdis/gridfunctions/ConstantGridFunction.hpp b/src/amdis/gridfunctions/ConstantGridFunction.hpp
index 978f8a5b..275da96f 100644
--- a/src/amdis/gridfunctions/ConstantGridFunction.hpp
+++ b/src/amdis/gridfunctions/ConstantGridFunction.hpp
@@ -27,6 +27,8 @@ namespace AMDiS
 
     using Geometry = typename LocalContext::Geometry;
 
+    enum { hasDerivative = true };
+
   public:
     ConstantLocalFunction(T const& value)
       : value_(value)
@@ -97,6 +99,8 @@ namespace AMDiS
     using LocalDomain = typename EntitySet::LocalCoordinate;
     using Range = Underlying_t<T>;
 
+    enum { hasDerivative = false };
+
   public:
     using LocalFunction = ConstantLocalFunction<Range(LocalDomain), Element, T>;
 
diff --git a/src/amdis/gridfunctions/DOFVectorView.hpp b/src/amdis/gridfunctions/DOFVectorView.hpp
index 91ddcb18..e71139e6 100644
--- a/src/amdis/gridfunctions/DOFVectorView.hpp
+++ b/src/amdis/gridfunctions/DOFVectorView.hpp
@@ -49,6 +49,7 @@ namespace AMDiS
     template <class Block>
     using Flat = Dune::Functions::FlatVectorBackend<Block>;
 
+    enum { hasDerivative = false };
 
   public: // a local view on the gradients
 
@@ -59,6 +60,8 @@ namespace AMDiS
       using Domain = LocalDomain;
       using Range = DerivativeRange;
 
+      enum { hasDerivative = false };
+
     private:
       using LocalBasisView = typename GlobalBasis::LocalView;
       using LocalIndexSet = typename GlobalBasis::LocalIndexSet;
@@ -135,6 +138,8 @@ namespace AMDiS
       using Domain = typename DOFVectorConstView::LocalDomain;
       using Range = typename DOFVectorConstView::Range;
 
+      enum { hasDerivative = true };
+
     private:
       using LocalBasisView = typename GlobalBasis::LocalView;
       using LocalIndexSet = typename GlobalBasis::LocalIndexSet;
diff --git a/src/amdis/gridfunctions/DerivativeGridFunction.hpp b/src/amdis/gridfunctions/DerivativeGridFunction.hpp
index 87fccfb8..e4c0adc7 100644
--- a/src/amdis/gridfunctions/DerivativeGridFunction.hpp
+++ b/src/amdis/gridfunctions/DerivativeGridFunction.hpp
@@ -32,6 +32,8 @@ namespace AMDiS
     using DerivativeTraits = Dune::Functions::DefaultDerivativeTraits<RawSignature>;
     using LocalFunction = std::decay_t<decltype(derivative(localFunction(std::declval<GridFunction>())))>;
 
+    enum { hasDerivative = false };
+
   public:
     /// The Range of the derivative of the GridFunction
     using Range = typename DerivativeTraits::Range;
@@ -58,9 +60,9 @@ namespace AMDiS
     }
 
     /// Return the derivative-localFunction of the GridFunction.
-    LocalFunction localFunction() const
+    friend LocalFunction localFunction(DerivativeGridFunction const& gf)
     {
-      return derivative(localFunction(gridFct_));
+      return derivative(localFunction(gf.gridFct_));
     }
 
     /// Return the \ref EntitySet of the \ref GridFunction.
@@ -74,16 +76,10 @@ namespace AMDiS
   };
 
 
-  template <class GF>
-  auto localFunction(DerivativeGridFunction<GF> const& gf)
-  {
-    return gf.localFunction();
-  }
-
-
+#ifndef DOXYGEN
   template <class GridFct,
             class LocalFct = decltype(localFunction(std::declval<GridFct>())),
-    REQUIRES(not Concepts::HasDerivative<GridFct>)>
+    REQUIRES(not GridFct::hasDerivative)>
   auto derivative(GridFct const& gridFct)
   {
     static_assert(Concepts::HasDerivative<LocalFct>, "derivative(LocalFunction) not defined!");
@@ -91,7 +87,6 @@ namespace AMDiS
   }
 
 
-#ifndef DOXYGEN
   template <class Expr>
   struct DerivativePreGridFunction
   {
diff --git a/src/amdis/gridfunctions/FunctorGridFunction.hpp b/src/amdis/gridfunctions/FunctorGridFunction.hpp
index f3158053..8b12ab25 100644
--- a/src/amdis/gridfunctions/FunctorGridFunction.hpp
+++ b/src/amdis/gridfunctions/FunctorGridFunction.hpp
@@ -9,7 +9,6 @@
 #include <amdis/common/IndexSeq.hpp>
 #include <amdis/common/Loops.hpp>
 #include <amdis/common/Mpl.hpp>
-#include <amdis/utility/Tuple.hpp>
 #include <amdis/gridfunctions/GridFunctionConcepts.hpp>
 
 namespace AMDiS
@@ -47,6 +46,8 @@ namespace AMDiS
     using Range = R;
     using Domain = D;
 
+    enum { hasDerivative = true };
+
     template <class LocalFct>
     struct LocalFunctionWrapper
     {
@@ -90,7 +91,7 @@ namespace AMDiS
     Range operator()(Domain const& x) const
     {
       using Dune::Std::apply;
-      return apply([&](auto&&... localFct) { return fct_(localFct(x)...); }, localFcts_);
+      return apply([&](auto&&... localFct) { return fct_((*localFct)(x)...); }, localFcts_);
     }
 
   public:
@@ -187,6 +188,8 @@ namespace AMDiS
     /// The set of entities this grid-function binds to
     using EntitySet = typename Impl::EntitySetType<GridFunctions...>::type;
 
+    enum { hasDerivative = false };
+
   private:
     template <class GridFct>
     using LocalFct = std::decay_t<decltype(localFunction(std::declval<GridFct>()))>;
@@ -234,7 +237,7 @@ namespace AMDiS
   template <class F, class... GFs>
   auto localFunction(FunctorGridFunction<F,GFs...> const& gf)
   {
-    return gt.localFunction();
+    return gf.localFunction();
   }
 
 
diff --git a/test/TupleUtilityTest.cpp b/test/TupleUtilityTest.cpp
index 4f40c2c3..9d99c3ba 100644
--- a/test/TupleUtilityTest.cpp
+++ b/test/TupleUtilityTest.cpp
@@ -14,13 +14,13 @@ int main()
   using TupleInt = std::tuple<int,int>;
   using Tuple2 = std::tuple<TupleDouble,TupleInt>;
 
-  Tuple1 u = {1.3, 2};
+  Tuple1 u{1.3, 2};
   auto v = constructTuple<Tuple1>(1.5);
   auto w = foldTuples<Tuple2>(u,v);
 
-  AMDIS_TEST(u == Tuple1({1.3, 2}));
-  AMDIS_TEST(v == Tuple1({1.5, 1}));
-  AMDIS_TEST(w == Tuple2( {{1.3, 1.5}, {2, 1}} ));
+  AMDIS_TEST((u == Tuple1{1.3, 2}));
+  AMDIS_TEST((v == Tuple1{1.5, 1}));
+  AMDIS_TEST((w == Tuple2{TupleDouble{1.3, 1.5}, TupleDouble{2, 1}} ));
 
   return report_errors();
 }
\ No newline at end of file
-- 
GitLab