DUNE-FUNCTIONS (unstable)

taylorhoodbasis.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_TAYLORHOODBASIS_HH
4 #define DUNE_FUNCTIONS_FUNCTIONSPACEBASES_TAYLORHOODBASIS_HH
5 
6 #include <dune/common/exceptions.hh>
7 #include <dune/common/reservedvector.hh>
8 #include <dune/common/indices.hh>
9 
10 #include <dune/typetree/powernode.hh>
11 #include <dune/typetree/compositenode.hh>
12 
13 #include <dune/functions/functionspacebases/nodes.hh>
14 
15 #include <dune/functions/functionspacebases/lagrangebasis.hh>
16 #include <dune/functions/functionspacebases/defaultglobalbasis.hh>
17 
18 namespace Dune {
19 namespace Functions {
20 
21 
22 // *****************************************************************************
23 // This is the reusable part of the basis. It contains
24 //
25 // TaylorHoodPreBasis
26 // TaylorHoodBasisTree
27 // TaylorHoodVelocityTree
28 //
29 // The pre-basis allows to create the others and is the owner of possible shared
30 // state. These components do _not_ depend on the global basis and local view
31 // and can be used without a global basis.
32 // *****************************************************************************
33 
34 template<typename GV>
35 class TaylorHoodVelocityTree;
36 
37 template<typename GV>
38 class TaylorHoodBasisTree;
39 
59 template<typename GV, bool HI=false>
61 {
62  static const bool useHybridIndices = HI;
63 
64  static const int dim = GV::dimension;
65 
66 public:
67 
69  using GridView = GV;
70 
72  using size_type = std::size_t;
73 
75  using Node = TaylorHoodBasisTree<GV>;
76 
77  static constexpr size_type maxMultiIndexSize = useHybridIndices ? 3 : 2;
78  static constexpr size_type minMultiIndexSize = 2;
79  static constexpr size_type multiIndexBufferSize = maxMultiIndexSize;
80 
81 private:
82 
85 
86 public:
87 
90  gridView_(gv),
91  pq1PreBasis_(gv),
92  pq2PreBasis_(gv)
93  {}
94 
97  {
98  pq1PreBasis_.initializeIndices();
99  pq2PreBasis_.initializeIndices();
100  }
101 
103  const GridView& gridView() const
104  {
105  return gridView_;
106  }
107 
109  void update (const GridView& gv)
110  {
111  pq1PreBasis_.update(gv);
112  pq2PreBasis_.update(gv);
113  }
114 
118  Node makeNode() const
119  {
120  return Node{};
121  }
122 
124  size_type size() const
125  {
126  return 2;
127  }
128 
130  template<class SizePrefix>
131  size_type size(const SizePrefix& prefix) const
132  {
133  return sizeImp<useHybridIndices>(prefix);
134  }
135 
136 private:
137 
138  template<bool hi, class SizePrefix,
139  std::enable_if_t<not hi,int> = 0>
140  size_type sizeImp(const SizePrefix& prefix) const
141  {
142  if (prefix.size() == 0)
143  return 2;
144  if (prefix.size() == 1)
145  {
146  if (prefix[0] == 0)
147  return dim * pq2PreBasis_.size();
148  if (prefix[0] == 1)
149  return pq1PreBasis_.size();
150  }
151  assert(prefix.size() == 2);
152  return 0;
153  }
154 
155  template<bool hi, class SizePrefix,
156  std::enable_if_t<hi,int> = 0>
157  size_type sizeImp(const SizePrefix& prefix) const
158  {
159  if (prefix.size() == 0)
160  return 2;
161  if (prefix.size() == 1)
162  {
163  if (prefix[0] == 0)
164  return pq2PreBasis_.size();
165  if (prefix[0] == 1)
166  return pq1PreBasis_.size();
167  }
168  if (prefix.size() == 2)
169  {
170  if (prefix[0] == 0)
171  return dim;
172  if (prefix[0] == 1)
173  return 0;
174  }
175  assert(prefix.size() == 3);
176  return 0;
177  }
178 
179 public:
180 
183  {
184  return dim * pq2PreBasis_.size() + pq1PreBasis_.size();
185  }
186 
189  {
190  return dim * pq2PreBasis_.maxNodeSize() + pq1PreBasis_.maxNodeSize();
191  }
192 
193  template<typename It>
194  It indices(const Node& node, It it) const
195  {
196  return indicesImp<useHybridIndices>(node, it);
197  }
198 
204  auto containerDescriptor() const
205  {
206  namespace CD = Dune::Functions::ContainerDescriptors;
207  if constexpr(HI)
208  return CD::makeDescriptor(
209  CD::makeUniformDescriptor(pq2PreBasis_.size(),
211  CD::FlatVector{pq1PreBasis_.size()});
212  else
213  return CD::Array<CD::FlatVector,2>{
214  CD::FlatVector{GV::dimension * pq2PreBasis_.size()},
215  CD::FlatVector{pq1PreBasis_.size()} };
216  }
217 
218 protected:
219 
220  template<class MultiIndex>
221  static const void multiIndexPushFront(MultiIndex& M, size_type M0)
222  {
223  M.resize(M.size()+1);
224  for(std::size_t i=M.size()-1; i>0; --i)
225  M[i] = M[i-1];
226  M[0] = M0;
227  }
228 
229  template<bool hi, class It,
230  std::enable_if_t<not hi,int> = 0>
231  It indicesImp(const Node& node, It multiIndices) const
232  {
233  using namespace Dune::Indices;
234  for(std::size_t child=0; child<dim; ++child)
235  {
236  size_type subTreeSize = node.child(_0, 0).size();
237  pq2PreBasis_.indices(node.child(_0, 0), multiIndices);
238  for (std::size_t i = 0; i<subTreeSize; ++i)
239  {
240  multiIndexPushFront(multiIndices[i], 0);
241  multiIndices[i][1] = multiIndices[i][1]*dim + child;
242  }
243  multiIndices += subTreeSize;
244  }
245  size_type subTreeSize = node.child(_1).size();
246  pq1PreBasis_.indices(node.child(_1), multiIndices);
247  for (std::size_t i = 0; i<subTreeSize; ++i)
248  multiIndexPushFront(multiIndices[i], 1);
249  multiIndices += subTreeSize;
250  return multiIndices;
251  }
252 
253  template<bool hi, class It,
254  std::enable_if_t<hi,int> = 0>
255  It indicesImp(const Node& node, It multiIndices) const
256  {
257  using namespace Dune::Indices;
258  for(std::size_t child=0; child<dim; ++child)
259  {
260  size_type subTreeSize = node.child(_0, 0).size();
261  pq2PreBasis_.indices(node.child(_0, 0), multiIndices);
262  for (std::size_t i = 0; i<subTreeSize; ++i)
263  {
264  multiIndexPushFront(multiIndices[i], 0);
265  multiIndices[i].push_back(i);
266  }
267  multiIndices += subTreeSize;
268  }
269  size_type subTreeSize = node.child(_1).size();
270  pq1PreBasis_.indices(node.child(_1), multiIndices);
271  for (std::size_t i = 0; i<subTreeSize; ++i)
272  multiIndexPushFront(multiIndices[i], 1);
273  multiIndices += subTreeSize;
274  return multiIndices;
275  }
276 
277  GridView gridView_;
278 
279  PQ1PreBasis pq1PreBasis_;
280  PQ2PreBasis pq2PreBasis_;
281 };
282 
283 
284 
285 template<typename GV>
286 class TaylorHoodVelocityTree :
287  public PowerBasisNode<LagrangeNode<GV,2>, GV::dimension>
288 {
289  using PQ2Node = LagrangeNode<GV,2>;
290  using Base = PowerBasisNode<PQ2Node, GV::dimension>;
291 
292 public:
293  TaylorHoodVelocityTree()
294  {
295  for(int i=0; i<GV::dimension; ++i)
296  this->setChild(i, std::make_shared<PQ2Node>());
297  }
298 };
299 
300 template<typename GV>
301 class TaylorHoodBasisTree :
302  public CompositeBasisNode<
303  TaylorHoodVelocityTree<GV>,
304  LagrangeNode<GV,1>
305  >
306 {
307  using VelocityNode=TaylorHoodVelocityTree<GV>;
308  using PressureNode=LagrangeNode<GV,1>;
309 
310  using Base=CompositeBasisNode<VelocityNode, PressureNode>;
311 
312 public:
313  TaylorHoodBasisTree()
314  {
315  this->template setChild<0>(std::make_shared<VelocityNode>());
316  this->template setChild<1>(std::make_shared<PressureNode>());
317  }
318 };
319 
320 
321 
322 namespace BasisFactory {
323 
330 inline auto taylorHood()
331 {
332  return [](const auto& gridView) {
333  return TaylorHoodPreBasis<std::decay_t<decltype(gridView)>>(gridView);
334  };
335 }
336 
337 } // end namespace BasisFactory
338 
339 // *****************************************************************************
340 // This is the actual global basis implementation based on the reusable parts.
341 // *****************************************************************************
342 
364 template<typename GV>
366 
367 
368 
369 } // end namespace Functions
370 } // end namespace Dune
371 
372 
373 #endif // DUNE_FUNCTIONS_FUNCTIONSPACEBASES_TAYLORHOODBASIS_HH
Global basis for given pre-basis.
Definition: defaultglobalbasis.hh:46
void initializeIndices()
Initialize the global indices.
Definition: lagrangebasis.hh:94
void update(const GridView &gv)
Update the stored grid view, to be called if the grid has changed.
Definition: lagrangebasis.hh:124
size_type maxNodeSize() const
Get the maximal number of DOFs associated to node for any element.
Definition: lagrangebasis.hh:168
size_type size(const SizePrefix &prefix) const
Return number of possible values for next position in multi index.
Definition: leafprebasismixin.hh:49
Pre-basis for lowest order Taylor-Hood basis.
Definition: taylorhoodbasis.hh:61
TaylorHoodPreBasis(const GridView &gv)
Constructor for a given grid view object.
Definition: taylorhoodbasis.hh:89
size_type size(const SizePrefix &prefix) const
Return number of possible values for next position in multi index.
Definition: taylorhoodbasis.hh:131
GV GridView
The grid view that the FE basis is defined on.
Definition: taylorhoodbasis.hh:69
const GridView & gridView() const
Obtain the grid view that the basis is defined on.
Definition: taylorhoodbasis.hh:103
void update(const GridView &gv)
Update the stored grid view, to be called if the grid has changed.
Definition: taylorhoodbasis.hh:109
auto containerDescriptor() const
Return an container descriptor depending on the flag HI. Either return a Tuple if hybrid indices shou...
Definition: taylorhoodbasis.hh:204
TaylorHoodBasisTree< GV > Node
Template mapping root tree path to type of created tree node.
Definition: taylorhoodbasis.hh:75
size_type size() const
Same as size(prefix) with empty prefix.
Definition: taylorhoodbasis.hh:124
size_type dimension() const
Get the total dimension of the space spanned by this basis.
Definition: taylorhoodbasis.hh:182
Node makeNode() const
Create tree node.
Definition: taylorhoodbasis.hh:118
void initializeIndices()
Initialize the global indices.
Definition: taylorhoodbasis.hh:96
size_type maxNodeSize() const
Get the maximal number of DOFs associated to node for any element.
Definition: taylorhoodbasis.hh:188
std::size_t size_type
Type used for indices and size information.
Definition: taylorhoodbasis.hh:72
auto taylorHood()
Create a pre-basis factory that can create a Taylor-Hood pre-basis.
Definition: taylorhoodbasis.hh:330
Definition: polynomial.hh:13
Descriptor for arrays with all children identical and the number of children a static size.
Definition: containerdescriptors.hh:125
Uniform descriptor with dynamic size.
Definition: containerdescriptors.hh:164
Creative Commons License   |  Legal Statements / Impressum  |  Hosted by TU Dresden  |  generated with Hugo v0.80.0 (May 16, 22:29, 2024)