DUNE PDELab (git)

nodes.hh
1// -*- tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2// vi: set et ts=4 sw=2 sts=2:
3#ifndef DUNE_FUNCTIONS_FUNCTIONSPACEBASES_NODES_HH
4#define DUNE_FUNCTIONS_FUNCTIONSPACEBASES_NODES_HH
5
6#include <cassert>
7#include <memory>
8
9#include <dune/common/indices.hh>
10
11#include <dune/typetree/leafnode.hh>
12#include <dune/typetree/powernode.hh>
13#include <dune/typetree/dynamicpowernode.hh>
14#include <dune/typetree/compositenode.hh>
15#include <dune/typetree/traversal.hh>
16#include <dune/typetree/visitor.hh>
17
18namespace Dune {
19 namespace Functions {
20
21
22 namespace Impl {
23
24
25 struct ClearSizeVisitor
26 : public TypeTree::TreeVisitor
27 , public TypeTree::DynamicTraversal
28 {
29
30 template<typename Node, typename TreePath>
31 void pre(Node& node, TreePath treePath)
32 {
33 leaf(node,treePath);
34 node.setSize(0);
35 }
36
37 template<typename Node, typename TreePath>
38 void leaf(Node& node, TreePath treePath)
39 {
40 node.setOffset(offset_);
41 }
42
43 ClearSizeVisitor(std::size_t offset)
44 : offset_(offset)
45 {}
46
47 const std::size_t offset_;
48
49 };
50
51
52 template<typename Entity>
53 struct BindVisitor
54 : public TypeTree::TreeVisitor
55 , public TypeTree::DynamicTraversal
56 {
57
58 template<typename Node, typename TreePath>
59 void pre(Node& node, TreePath)
60 {
61 node.setOffset(offset_);
62 }
63
64 template<typename Node, typename TreePath>
65 void post(Node& node, TreePath)
66 {
67 node.setSize(offset_ - node.offset());
68 }
69
70 template<typename Node, typename TreePath>
71 void leaf(Node& node, TreePath)
72 {
73 node.setOffset(offset_);
74 node.bind(entity_);
75 offset_ += node.size();
76 }
77
78 BindVisitor(const Entity& entity, std::size_t offset = 0)
79 : entity_(entity)
80 , offset_(offset)
81 {}
82
83 const Entity& entity_;
84 std::size_t offset_;
85
86 };
87
88
89 struct InitializeTreeVisitor :
90 public TypeTree::TreeVisitor,
91 public TypeTree::DynamicTraversal
92 {
93 template<typename Node, typename TreePath>
94 void pre(Node& node, TreePath)
95 {
96 node.setTreeIndex(treeIndex_);
97 ++treeIndex_;
98 }
99
100 template<typename Node, typename TreePath>
101 void leaf(Node& node, TreePath)
102 {
103 node.setTreeIndex(treeIndex_);
104 ++treeIndex_;
105 }
106
107 InitializeTreeVisitor(std::size_t treeIndexOffset = 0) :
108 treeIndex_(treeIndexOffset)
109 {}
110
111 std::size_t treeIndex_;
112 };
113
114 } // end namespace Impl
115
116
117 class BasisNodeMixin
118 {
119
120 friend struct Impl::ClearSizeVisitor;
121
122 template<typename>
123 friend struct Impl::BindVisitor;
124
125 friend struct Impl::InitializeTreeVisitor;
126
127 public:
128
129 using size_type = std::size_t;
130
131 BasisNodeMixin() :
132 offset_(0),
133 size_(0),
134 treeIndex_(0)
135 {}
136
137 size_type localIndex(size_type i) const
138 {
139 assert(i < size_);
140 return offset_ + i;
141 }
142
143 size_type size() const
144 {
145 return size_;
146 }
147
148 size_type treeIndex() const
149 {
150 return treeIndex_;
151 }
152
153 protected:
154
155 size_type offset() const
156 {
157 return offset_;
158 }
159
160 void setOffset(const size_type offset)
161 {
162 offset_ = offset;
163 }
164
165 void setSize(const size_type size)
166 {
167 size_ = size;
168 }
169
170 void setTreeIndex(size_type treeIndex)
171 {
172 treeIndex_ = treeIndex;
173 }
174
175 private:
176
177 size_type offset_;
178 size_type size_;
179 size_type treeIndex_;
180
181 };
182
183
184 class LeafBasisNode :
185 public BasisNodeMixin,
186 public TypeTree::LeafNode
187 {};
188
189
190 template<typename T, std::size_t n>
191 class PowerBasisNode :
192 public BasisNodeMixin,
193 public TypeTree::PowerNode<T,n>
194 {
195
196 using Node = TypeTree::PowerNode<T,n>;
197
198 public:
199
200 using Element = typename T::Element;
201
202 PowerBasisNode() = default;
203
204 PowerBasisNode(const typename Node::NodeStorage& children) :
205 Node(children)
206 {}
207
208 const Element& element() const
209 {
210 return this->child(Dune::Indices::_0).element();
211 }
212
213 };
214
215
216 template<typename T>
217 class DynamicPowerBasisNode :
218 public BasisNodeMixin,
219 public TypeTree::DynamicPowerNode<T>
220 {
221
222 using Node = TypeTree::DynamicPowerNode<T>;
223
224 public:
225
226 using Element = typename T::Element;
227
228 DynamicPowerBasisNode (std::size_t children)
229 : Node(children)
230 {}
231
232 DynamicPowerBasisNode (typename Node::NodeStorage children)
233 : Node(std::move(children))
234 {}
235
236 const Element& element() const
237 {
238 return this->child(0).element();
239 }
240
241 };
242
243
244 template<typename... T>
245 class CompositeBasisNode :
246 public BasisNodeMixin,
247 public TypeTree::CompositeNode<T...>
248 {
249
250 using Node = TypeTree::CompositeNode<T...>;
251
252 public:
253
254 using Element = typename Node::template Child<0>::Type::Element;
255
256 CompositeBasisNode() = default;
257
258 CompositeBasisNode(const typename Node::NodeStorage& children) :
259 Node(children)
260 {}
261
262 template<typename... Children>
263 CompositeBasisNode(const std::shared_ptr<Children>&... children) :
264 Node(children...)
265 {}
266
267 const Element& element() const
268 {
269 return this->child(Dune::Indices::_0).element();
270 }
271
272 };
273
274
275 template<typename Tree>
276 void clearSize(Tree& tree, std::size_t offset)
277 {
278 TypeTree::applyToTree(tree,Impl::ClearSizeVisitor(offset));
279 }
280
281 template<typename Tree, typename Entity>
282 void bindTree(Tree& tree, const Entity& entity, std::size_t offset = 0)
283 {
284 Impl::BindVisitor<Entity> visitor(entity,offset);
285 TypeTree::applyToTree(tree,visitor);
286 }
287
288 template<typename Tree>
289 void initializeTree(Tree& tree, std::size_t treeIndexOffset = 0)
290 {
291 Impl::InitializeTreeVisitor visitor(treeIndexOffset);
292 TypeTree::applyToTree(tree,visitor);
293 }
294
295
296 } // namespace Functions
297
298} // namespace Dune
299
300#endif // DUNE_FUNCTIONS_FUNCTIONSPACEBASES_NODES_HH
std::tuple< std::shared_ptr< Children >... > NodeStorage
The type used for storing the children.
Definition: compositenode.hh:36
std::vector< ChildStorageType > NodeStorage
The type used for storing the children.
Definition: dynamicpowernode.hh:67
std::array< std::shared_ptr< T >, k > NodeStorage
The type used for storing the children.
Definition: powernode.hh:77
constexpr index_constant< 0 > _0
Compile time index with value 0.
Definition: indices.hh:52
constexpr auto treePath(const T &... t)
Constructs a new HybridTreePath from the given indices.
Definition: treepath.hh:326
void applyToTree(Tree &&tree, Visitor &&visitor)
Apply visitor to TypeTree.
Definition: traversal.hh:239
ImplementationDefined child(Node &&node, Indices... indices)
Extracts the child of a node given by a sequence of compile-time and run-time indices.
Definition: childextraction.hh:128
Dune namespace.
Definition: alignedallocator.hh:13
constexpr std::integral_constant< std::size_t, sizeof...(II)> size(std::integer_sequence< T, II... >)
Return the size of the sequence.
Definition: integersequence.hh:75
STL namespace.
void post(T &&, TreePath) const
Method for postfix tree traversal.
Definition: visitor.hh:83
void leaf(T &&, TreePath) const
Method for leaf traversal.
Definition: visitor.hh:93
void pre(T &&, TreePath) const
Method for prefix tree traversal.
Definition: visitor.hh:60
Creative Commons License   |  Legal Statements / Impressum  |  Hosted by TU Dresden  |  generated with Hugo v0.111.3 (Jul 15, 22:36, 2024)