AMDiS  0.3
The Adaptive Multi-Dimensional Simulation Toolbox
OperatorList.hpp
1 #pragma once
2 
3 #include <list>
4 #include <memory>
5 
6 #include <amdis/BoundarySubset.hpp>
7 #include <amdis/ContextGeometry.hpp>
8 #include <amdis/Operator.hpp>
9 #include <amdis/typetree/TreeContainer.hpp>
10 
11 namespace AMDiS
12 {
13  namespace tag
14  {
15  template <class E> struct element_operator { using type = E; };
16  template <class I> struct intersection_operator { using type = I; };
17 
18  template <class I>
20  : public BoundarySubset<I>
21  {
22  using type = I;
23 
25  : BoundarySubset<I>{bs}
26  {}
27 
29  };
30  }
31 
32  template <class GridView, class Container>
34  {
35  using Element = typename GridView::template Codim<0>::Entity;
36  using Intersection = typename GridView::Intersection;
37 
38  using ElementTraits = Impl::OperatorTraits<GridView,Element,Container>;
39  using IntersectionTraits = Impl::OperatorTraits<GridView,Intersection,Container>;
40 
41  template <class Op>
42  struct DataElement
43  {
44  Op op;
46 
47  friend auto localOperator(DataElement const& de)
48  {
49  return DataElement<decltype(localOperator(de.op))>{localOperator(de.op), de.bs};
50  }
51  };
52 
55  template <class... Nodes>
56  struct LocalData
57  {
59  bool empty() const
60  {
61  return element_.empty() && boundary_.empty() && intersection_.empty();
62  }
63 
65  void bind(Element const& elem)
66  {
67  for (auto& op : element_) op.bind(elem);
68  for (auto& op : intersection_) op.bind(elem);
69  for (auto& data : boundary_) data.op.bind(elem);
70  }
71 
73  void unbind()
74  {
75  for (auto& op : element_) op.unbind();
76  for (auto& op : intersection_) op.unbind();
77  for (auto& data : boundary_) data.op.unbind();
78  assembled_ = true;
79  }
80 
82  void assemble(GlobalContext<GridView> const& context, Nodes const&... nodes,
83  Container& matVec) const
84  {
85  // do not assemble in case nothing to do
86  if ((assembled_ && !changing_) || empty())
87  return;
88 
89  // create a context for the element
90  ContextGeometry elementContext{context.element(), context.element(), context.geometry()};
91 
92  // assemble element operators
93  for (auto const& op : element_)
94  op.assemble(elementContext, nodes..., matVec);
95 
96  if (intersection_.empty() && (boundary_.empty() || !context.element().hasBoundaryIntersections()))
97  return;
98 
99  // assemble intersection operators
100  for (auto const& is : intersections(context.gridView(), context.element()))
101  {
102  // create a context for the intersection
103  ContextGeometry intersectionContext{is, context.element(), context.geometry()};
104 
105  if (is.boundary()) {
106  // assemble boundary operators
107  for (auto& data : boundary_) {
108  if (data.bs(is))
109  data.op.assemble(intersectionContext, nodes..., matVec);
110  }
111  } else {
112  // assemble intersection operators
113  for (auto& op : intersection_)
114  op.assemble(intersectionContext, nodes..., matVec);
115  }
116  }
117  }
118 
120  using ElementOperator = LocalOperator<ElementTraits, Nodes...>;
121 
123  using IntersectionOperator = LocalOperator<IntersectionTraits, Nodes...>;
124 
126  std::vector<ElementOperator> element_;
127 
129  std::vector<IntersectionOperator> intersection_;
130 
132  std::vector<DataElement<IntersectionOperator>> boundary_;
133 
135  bool assembled_ = false;
136 
138  bool changing_ = true;
139  };
140 
141 
142  template <class... Nodes>
143  struct Data
144  {
145  void update(GridView const& gridView)
146  {
147  for (auto& e : element_)
148  e.update(gridView);
149  for (auto& is : intersection_)
150  is.update(gridView);
151  for (auto& b : boundary_)
152  b.op.update(gridView);
153  }
154 
155  template <class Op>
156  void push(tag::element_operator<Element>, Op&& op)
157  {
158  element_.emplace_back(FWD(op));
159  }
160 
161  template <class Op>
162  void push(tag::intersection_operator<Intersection>, Op&& op)
163  {
164  intersection_.emplace_back(FWD(op));
165  }
166 
167  template <class Op>
168  void push(tag::boundary_operator<Intersection> b, Op&& op)
169  {
170  boundary_.push_back({FWD(op), b});
171  }
172 
173  friend LocalData<Nodes...> localOperator(Data const& d)
174  {
175  LocalData<Nodes...> data;
176  for (auto const& e : d.element_)
177  data.element_.push_back(localOperator(e));
178  for (auto const& is : d.intersection_)
179  data.intersection_.push_back(localOperator(is));
180  for (auto const& b : d.boundary_)
181  data.boundary_.push_back(localOperator(b));
182  return data;
183  }
184 
186  using ElementOperator = Operator<ElementTraits, Nodes...>;
187 
189  using IntersectionOperator = Operator<IntersectionTraits, Nodes...>;
190 
192  std::vector<ElementOperator> element_;
193 
195  std::vector<IntersectionOperator> intersection_;
196 
198  std::vector<DataElement<IntersectionOperator>> boundary_;
199  };
200 
201  public:
202 
204  template <class RowNode, class ColNode>
205  using MatData = Data<RowNode, ColNode>;
206 
207  template <class RowNode, class ColNode>
208  using LocalMatData = LocalData<RowNode, ColNode>;
209 
211  template <class Node>
212  using VecData = Data<Node>;
213 
214  template <class Node>
215  using LocalVecData = LocalData<Node>;
216  };
217 
218 
219  template <class RowBasis, class ColBasis, class ElementMatrix>
220  using MatrixOperators
221  = TypeTree::TreeMatrix<
223  typename RowBasis::LocalView::TreeCache,
224  typename ColBasis::LocalView::TreeCache>;
225 
226  template <class Basis, class ElementVector>
227  using VectorOperators
228  = TypeTree::TreeContainer<
230  typename Basis::LocalView::TreeCache>;
231 
232 } // end namespace AMDiS
Class defining a subset of a domain boundary.
Definition: BoundarySubset.hpp:22
GridView const & gridView() const
Return the GridView this context is bound to.
Definition: ContextGeometry.hpp:190
Definition: ContextGeometry.hpp:168
The base class for an operator to be used in an Assembler.
Definition: Operator.hpp:79
Data< RowNode, ColNode > MatData
List of operators associated with matrix blocks (RowNode, ColNode)
Definition: OperatorList.hpp:205
Definition: OperatorList.hpp:33
Definition: AdaptBase.hpp:6
Definition: OperatorList.hpp:19
Geometry const & geometry() const
Return the geometry of the Element.
Definition: ContextGeometry.hpp:202
Data< Node > VecData
List of operators associated with vector blocks [Node].
Definition: OperatorList.hpp:212
The base class for a local operator to be used in a Assembler.
Definition: LocalOperator.hpp:73
Wrapper class for element and geometry.
Definition: ContextGeometry.hpp:43
Definition: OperatorList.hpp:15
Definition: OperatorList.hpp:16
Element const & element() const
Return the bound element (entity of codim 0)
Definition: ContextGeometry.hpp:196