dune-pdelab  2.0.0
permutationordering.hh
Go to the documentation of this file.
1 // -*- tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2 // vi: set et ts=8 sw=2 sts=2:
3 
4 #ifndef DUNE_PDELAB_ORDERING_PERMUTATIONORDERING_HH
5 #define DUNE_PDELAB_ORDERING_PERMUTATIONORDERING_HH
6 
7 #include <cstddef>
8 #include <ostream>
9 #include <string>
10 
11 #include <dune/common/classname.hh>
12 #include <dune/common/exceptions.hh>
13 #include <dune/common/stdstreams.hh>
14 
15 #include <dune/typetree/compositenodemacros.hh>
16 #include <dune/typetree/powernode.hh>
17 #include <dune/typetree/traversal.hh>
18 #include <dune/typetree/visitor.hh>
19 
24 
25 namespace Dune {
26  namespace PDELab {
27 
30 
31  namespace permutation_ordering {
32 
34  template<typename DI, typename CI, typename Node>
35  class Base
36  : public lexicographic_ordering::Base<DI,CI,Node>,
37  public VirtualOrderingBase<DI,CI>
38  {
39 
40  public:
41 
44  typedef typename BaseT::Traits Traits;
45 
47 
48  static const bool consume_tree_index = true;
49 
51 
56  Base(Node& node, bool container_blocked, const OrderingTag& ordering_tag)
57  : BaseT(node,container_blocked),
58  _perm(ordering_tag.permutation())
59  {
60  // Make sure to use 'this' as a delegate in OrderingBase, so the virtual function call
61  // to 'map_index_dynamic' is found!
62  this->setDelegate(this);
63  }
64 
66  Base(const This& other)
67  : BaseT(other),
68  _perm(other._perm)
69  {
70  // Make sure to use 'this' as a delegate in OrderingBase, so the virtual function call
71  // to 'map_index_dynamic' is found!
72  this->setDelegate(this);
73  }
74 
75  Base(This&& other)
76  : BaseT(std::move(other)),
77  _perm(std::move(other._perm))
78  {
79  // Make sure to use 'this' as a delegate in OrderingBase, so the virtual function call
80  // to 'map_index_dynamic' is found!
81  this->setDelegate(this);
82  }
83 
84  template<typename ItIn, typename ItOut>
85  void map_lfs_indices(const ItIn begin, const ItIn end, ItOut out) const
86  {
87  BaseT::map_lfs_indices(begin,end,out);
88 
89  // Permute indices
90  for (ItIn in = begin; in != end; ++in, ++out)
91  out->back() = _perm[out->back()];
92  }
93 
94  template<typename CIOutIterator, typename DIOutIterator = DummyDOFIndexIterator>
95  typename Traits::SizeType
96  extract_entity_indices(const typename Traits::DOFIndex::EntityIndex& ei,
97  typename Traits::SizeType child_index,
98  CIOutIterator ci_out, const CIOutIterator ci_end) const
99  {
100  BaseT::extract_entity_indices(ei,child_index,ci_out,ci_end);
101 
102  // Permute indices
103  for (; ci_out != ci_end; ++ci_out)
104  {
105  ci_out->back() = _perm[ci_out->back()];
106  }
107 
108  // The return value is not used for non-leaf orderings.
109  return 0;
110  }
111 
112  virtual void map_index_dynamic(typename Traits::DOFIndexView di, typename Traits::ContainerIndex& ci) const
113  {
114  this->_mapIndex(di,ci);
115 
116  // Permute index
117  ci.back() = _perm[ci.back()];
118  }
119 
120  private:
121  const std::vector<std::size_t>& _perm;
122 
123  };
124  }
125 
127  template<typename DI, typename CI, typename Child, std::size_t k>
129  : public TypeTree::PowerNode<Child, k>
130  , public permutation_ordering::Base<DI,
131  CI,
132  PowerLexicographicOrdering<DI,CI,Child,k>
133  >
134  {
135  typedef TypeTree::PowerNode<Child, k> Node;
136 
137  typedef permutation_ordering::Base<DI,
138  CI,
140  > Base;
141 
142  public:
143 
145 
153  PowerPermutationOrdering(bool container_blocked, const PermutationOrderingTag& ordering_tag, const typename Node::NodeStorage& children)
154  : Node(children)
155  , Base(*this,container_blocked,ordering_tag)
156  { }
157 
158  void update()
159  {
160  for (std::size_t i = 0; i < Node::CHILDREN; ++i)
161  {
162  this->child(i).update();
163  }
164  Base::update();
165  }
166 
167  std::string name() const { return "PowerPermutationOrdering"; }
168  };
169 
170 
171  template<typename GFS, typename Transformation>
172  struct power_gfs_to_ordering_descriptor<GFS,Transformation,PermutationOrderingTag>
173  {
174 
175  static const bool recursive = true;
176 
177  template<typename TC>
178  struct result
179  {
180 
181  typedef PowerPermutationOrdering<
182  typename Transformation::DOFIndex,
183  typename Transformation::ContainerIndex,
184  TC,
185  GFS::CHILDREN
186  > type;
187 
188  typedef shared_ptr<type> storage_type;
189 
190  };
191 
192  template<typename TC>
193  static typename result<TC>::type transform(const GFS& gfs, const Transformation& t, const array<shared_ptr<TC>,GFS::CHILDREN>& children)
194  {
195  return typename result<TC>::type(gfs.backend().blocked(gfs),gfs->orderingTag(),children);
196  }
197 
198  template<typename TC>
199  static typename result<TC>::storage_type transform_storage(shared_ptr<const GFS> gfs, const Transformation& t, const array<shared_ptr<TC>,GFS::CHILDREN>& children)
200  {
201  return make_shared<typename result<TC>::type>(gfs->backend().blocked(*gfs),gfs->orderingTag(),children);
202  }
203 
204  };
205 
206  // the generic registration for PowerGridFunctionSpace happens in transformations.hh
207 
208 
210  template<typename DI, typename CI, DUNE_TYPETREE_COMPOSITENODE_TEMPLATE_CHILDREN>
212  public DUNE_TYPETREE_COMPOSITENODE_BASETYPE,
213  public permutation_ordering::Base<DI,
214  CI,
215  CompositePermutationOrdering<
216  DI,
217  CI,
218  DUNE_TYPETREE_COMPOSITENODE_CHILDTYPES
219  >
220  >
221  {
222  typedef DUNE_TYPETREE_COMPOSITENODE_BASETYPE Node;
223 
225  DI,
226  CI,
228  DI,
229  CI,
230  DUNE_TYPETREE_COMPOSITENODE_CHILDTYPES
231  >
232  > Base;
233 
234  public:
236 
244  CompositePermutationOrdering(bool backend_blocked, const PermutationOrderingTag& ordering_tag,
245  DUNE_TYPETREE_COMPOSITENODE_STORAGE_CONSTRUCTOR_SIGNATURE)
246  : Node(DUNE_TYPETREE_COMPOSITENODE_CHILDVARIABLES)
247  , Base(*this,backend_blocked,ordering_tag)
248  { }
249 
250  std::string name() const { return "CompositePermutationOrdering"; }
251 
252  void update()
253  {
254  TypeTree::applyToTree(*this,ordering::update_direct_children());
255  Base::update();
256  }
257  };
258 
259 #if HAVE_VARIADIC_TEMPLATES
260 
261  template<typename GFS, typename Transformation>
262  struct composite_gfs_to_ordering_descriptor<GFS,Transformation,PermutationOrderingTag>
263  {
264 
265  static const bool recursive = true;
266 
267  template<typename... TC>
268  struct result
269  {
270 
271  typedef CompositePermutationOrdering<
272  typename Transformation::DOFIndex,
273  typename Transformation::ContainerIndex,
274  TC...
275  > type;
276 
277  typedef shared_ptr<type> storage_type;
278 
279  };
280 
281  template<typename... TC>
282  static typename result<TC...>::type transform(const GFS& gfs, const Transformation& t, shared_ptr<TC>... children)
283  {
284  return typename result<TC...>::type(gfs.backend().blocked(gfs),gfs.orderingTag(),children...);
285  }
286 
287  template<typename... TC>
288  static typename result<TC...>::storage_type transform_storage(shared_ptr<const GFS> gfs, const Transformation& t, shared_ptr<TC>... children)
289  {
290  return make_shared<typename result<TC...>::type>(gfs->backend().blocked(*gfs),gfs.orderingTag(),children...);
291  }
292 
293  };
294 
295 #else // HAVE_VARIADIC_TEMPLATES
296 
298  template<typename GFS, typename Transformation>
299  struct composite_gfs_to_ordering_descriptor<GFS,Transformation,PermutationOrderingTag>
300  {
301 
302  static const bool recursive = true;
303 
304  template<typename TC0,
305  typename TC1,
306  typename TC2,
307  typename TC3,
308  typename TC4,
309  typename TC5,
310  typename TC6,
311  typename TC7,
312  typename TC8,
313  typename TC9>
314  struct result
315  {
316  // TODO: FIXME - this has not been changed to new interface yet!
317  typedef CompositePermutationOrdering<typename Transformation::GridFunctionSpace::Traits::SizeType,
318  TC0,TC1,TC2,TC3,TC4,TC5,TC6,TC7,TC8,TC9> type;
319  typedef shared_ptr<type> storage_type;
320  };
321 
322  template<typename TC0,
323  typename TC1,
324  typename TC2,
325  typename TC3,
326  typename TC4,
327  typename TC5,
328  typename TC6,
329  typename TC7,
330  typename TC8,
331  typename TC9>
333  transform(const GFSNode& s,
334  const Transformation& t,
335  shared_ptr<TC0> c0,
336  shared_ptr<TC1> c1,
337  shared_ptr<TC2> c2,
338  shared_ptr<TC3> c3,
339  shared_ptr<TC4> c4,
340  shared_ptr<TC5> c5,
341  shared_ptr<TC6> c6,
342  shared_ptr<TC7> c7,
343  shared_ptr<TC8> c8,
344  shared_ptr<TC9> c9)
345  {
346  return typename result<TC0,TC1,TC2,TC3,TC4,TC5,TC6,TC7,TC8,TC9>::type(t.asGridFunctionSpace(s),t.asGridFunctionSpace(s).orderingTag(),c0,c1,c2,c3,c4,c5,c6,c7,c8,c9);
347  }
348 
349  template<typename TC0,
350  typename TC1,
351  typename TC2,
352  typename TC3,
353  typename TC4,
354  typename TC5,
355  typename TC6,
356  typename TC7,
357  typename TC8,
358  typename TC9>
359  static typename result<TC0,TC1,TC2,TC3,TC4,TC5,TC6,TC7,TC8,TC9>::storage_type
360  transform_storage(shared_ptr<const GFSNode> s,
361  const Transformation& t,
362  shared_ptr<TC0> c0,
363  shared_ptr<TC1> c1,
364  shared_ptr<TC2> c2,
365  shared_ptr<TC3> c3,
366  shared_ptr<TC4> c4,
367  shared_ptr<TC5> c5,
368  shared_ptr<TC6> c6,
369  shared_ptr<TC7> c7,
370  shared_ptr<TC8> c8,
371  shared_ptr<TC9> c9)
372  {
373  return make_shared<typename result<TC0,TC1,TC2,TC3,TC4,TC5,TC6,TC7,TC8,TC9>::type>(t.asGridFunctionSpace(s),t.asGridFunctionSpace(s).orderingTag(),c0,c1,c2,c3,c4,c5,c6,c7,c8,c9);
374  }
375 
376  };
377 
378 #endif // HAVE_VARIADIC_TEMPLATES
379 
380  // the generic registration for PowerGridFunctionSpace happens in transformations.hh
381 
383  } // namespace PDELab
384 } // namespace Dune
385 
386 #endif // DUNE_PDELAB_ORDERING_PERMUTATIONORDERING_HH
CompositePermutationOrdering< typename Transformation::GridFunctionSpace::Traits::SizeType, TC0, TC1, TC2, TC3, TC4, TC5, TC6, TC7, TC8, TC9 > type
Definition: permutationordering.hh:318
BaseT::Traits Traits
Definition: permutationordering.hh:44
Base(Node &node, bool container_blocked, const OrderingTag &ordering_tag)
Construct ordering object.
Definition: permutationordering.hh:56
void map_lfs_indices(const ItIn begin, const ItIn end, ItOut out) const
Definition: permutationordering.hh:85
lexicographic_ordering::Base< DI, CI, Node > BaseT
Definition: permutationordering.hh:43
CompositePermutationOrdering(bool backend_blocked, const PermutationOrderingTag &ordering_tag, DUNE_TYPETREE_COMPOSITENODE_STORAGE_CONSTRUCTOR_SIGNATURE)
Construct ordering object.
Definition: permutationordering.hh:244
Traits::SizeType extract_entity_indices(const typename Traits::DOFIndex::EntityIndex &ei, typename Traits::SizeType child_index, CIOutIterator ci_out, const CIOutIterator ci_end) const
Definition: permutationordering.hh:96
DI::size_type SizeType
Definition: ordering/utility.hh:201
Indicate lexicographic ordering of the unknowns of non-leaf grid function spaces. ...
Definition: gridfunctionspace/tags.hh:59
Base(This &&other)
Definition: permutationordering.hh:75
void _mapIndex(typename Traits::DOFIndexView di, typename Traits::ContainerIndex &ci) const
Definition: orderingbase.hh:232
void map_lfs_indices(const ItIn begin, const ItIn end, ItOut out) const
Definition: lexicographicordering.hh:59
CI ContainerIndex
Definition: ordering/utility.hh:160
Definition: orderingbase.hh:22
void update()
Definition: permutationordering.hh:158
Definition: ordering/utility.hh:230
void update()
Definition: permutationordering.hh:252
Definition: ordering/utility.hh:186
Indicate permuted ordering of the unknowns of non-leaf grid function spaces according to a given perm...
Definition: gridfunctionspace/tags.hh:134
PowerPermutationOrdering(bool container_blocked, const PermutationOrderingTag &ordering_tag, const typename Node::NodeStorage &children)
Construct ordering object.
Definition: permutationordering.hh:153
PermutationOrderingTag OrderingTag
Definition: permutationordering.hh:46
Interface for merging index spaces.
Definition: permutationordering.hh:211
Traits::SizeType extract_entity_indices(const typename Traits::DOFIndex::EntityIndex &ei, typename Traits::SizeType child_index, CIOutIterator ci_out, const CIOutIterator ci_end) const
Definition: lexicographicordering.hh:75
Base< DI, CI, Node > This
Definition: permutationordering.hh:42
Interface for merging index spaces.
Definition: permutationordering.hh:35
Definition: lexicographicordering.hh:104
static result< TC >::storage_type transform_storage(shared_ptr< const GFS > gfs, const Transformation &t, const array< shared_ptr< TC >, GFS::CHILDREN > &children)
Definition: permutationordering.hh:199
Interface for merging index spaces.
Definition: permutationordering.hh:128
void update()
Definition: orderingbase.hh:100
virtual void map_index_dynamic(typename Traits::DOFIndexView di, typename Traits::ContainerIndex &ci) const
Definition: permutationordering.hh:112
std::string name() const
Definition: permutationordering.hh:250
static result< TC0, TC1, TC2, TC3, TC4, TC5, TC6, TC7, TC8, TC9 >::storage_type transform_storage(shared_ptr< const GFSNode > s, const Transformation &t, shared_ptr< TC0 > c0, shared_ptr< TC1 > c1, shared_ptr< TC2 > c2, shared_ptr< TC3 > c3, shared_ptr< TC4 > c4, shared_ptr< TC5 > c5, shared_ptr< TC6 > c6, shared_ptr< TC7 > c7, shared_ptr< TC8 > c8, shared_ptr< TC9 > c9)
Definition: permutationordering.hh:360
static result< TC >::type transform(const GFS &gfs, const Transformation &t, const array< shared_ptr< TC >, GFS::CHILDREN > &children)
Definition: permutationordering.hh:193
DI::View DOFIndexView
Definition: ordering/utility.hh:198
std::string name() const
Definition: permutationordering.hh:167
static result< TC0, TC1, TC2, TC3, TC4, TC5, TC6, TC7, TC8, TC9 >::type transform(const GFSNode &s, const Transformation &t, shared_ptr< TC0 > c0, shared_ptr< TC1 > c1, shared_ptr< TC2 > c2, shared_ptr< TC3 > c3, shared_ptr< TC4 > c4, shared_ptr< TC5 > c5, shared_ptr< TC6 > c6, shared_ptr< TC7 > c7, shared_ptr< TC8 > c8, shared_ptr< TC9 > c9)
Definition: permutationordering.hh:333
PowerPermutationOrdering< typename Transformation::DOFIndex, typename Transformation::ContainerIndex, TC, GFS::CHILDREN > type
Definition: permutationordering.hh:186
Base(const This &other)
Copy constructor.
Definition: permutationordering.hh:66
static const bool consume_tree_index
Definition: permutationordering.hh:48
const std::string s
Definition: function.hh:1103
Definition: lexicographicordering.hh:33
void setDelegate(const VirtualOrderingBase< DI, CI > *delegate)
Set the delegate called in mapIndex().
Definition: orderingbase.hh:227