7 #include <dune/common/exceptions.hh> 8 #include <dune/common/hybridutilities.hh> 9 #include <dune/common/version.hh> 10 #include <dune/functions/functionspacebases/nodes.hh> 11 #include <dune/functions/functionspacebases/lagrangebasis.hh> 12 #include <dune/grid/common/gridenums.hh> 13 #include <dune/localfunctions/common/localkey.hh> 15 #include <amdis/Output.hpp> 16 #include <amdis/common/Apply.hpp> 17 #include <amdis/common/ConceptsBase.hpp> 18 #include <amdis/common/ForEach.hpp> 19 #include <amdis/common/TupleUtility.hpp> 20 #include <amdis/functions/Nodes.hpp> 21 #include <amdis/utility/Twist.hpp> 28 template <
class GV,
int k,
class MI>
29 class LagrangeDGPreBasis;
31 template<
typename GV,
class MI,
bool HI>
32 class TaylorHoodPreBasis;
40 template <class PreBasis, class TP, class NodeTag = typename Node_t<PreBasis,TP>::NodeTag>
48 template <
class EntityIdType>
51 using Super = std::pair<EntityIdType, std::size_t>;
55 : Super(EntityIdType{}, i)
73 friend std::ostream& operator<<(std::ostream& os,
GlobalIdType const&
id)
75 os <<
"(" <<
id.first <<
"," <<
id.second <<
")";
80 template <
class Basis>
106 template <
class GB,
class = std::
void_t<> >
110 using GlobalBasis = GB;
111 using Tree =
typename GB::LocalView::Tree;
112 using size_type = std::size_t;
115 using Grid =
typename GridView::Grid;
116 using Element =
typename GridView::template Codim<0>::Entity;
117 using EntityIdType =
typename Grid::GlobalIdSet::IdType;
118 using PartitionType = Dune::PartitionType;
122 using TreePath =
typename GlobalBasis::PrefixPath;
128 : tree_(globalBasis.localView().tree())
129 , nodeIdSet_(globalBasis.gridView())
130 , twist_(globalBasis.gridView().grid().globalIdSet())
132 initializeTree(tree_);
141 void bind(Element
const& element)
143 bindTree(tree_, element);
144 nodeIdSet_.bind(tree_);
145 twist_.bind(element);
146 data_.resize(size());
147 nodeIdSet_.fillIn(twist_, data_.begin());
166 assert( i < data_.size() );
167 return data_[i].first;
181 assert( i < data_.size() );
182 return data_[i].second;
189 using Data = std::pair<IdType, PartitionType>;
190 std::vector<Data> data_;
195 template <
class Basis>
206 template <
class PB,
class TP,
class NodeTag>
211 using Node = Node_t<PreBasis,TP>;
212 using GridView =
typename PreBasis::GridView;
213 using size_type = std::size_t;
215 static_assert(Node::isLeaf,
"Generic NodeIdSet implemented for LeafNodes only. Provide a specialization for your node!");
218 static constexpr
int dim = GridView::template Codim<0>::Entity::mydimension;
222 : gridView_(gridView)
230 size_ = node_->finiteElement().size();
232 std::fill(std::begin(sizes_), std::end(sizes_), 0u);
233 for (size_type i = 0; i < size_ ; ++i) {
234 Dune::LocalKey
const& localKey = node_->finiteElement().localCoefficients().localKey(i);
235 sizes_[localKey.codim()]++;
237 auto refElem = Dune::referenceElement<double,GridView::dimension>(node_->element().type());
238 for (size_type c = 0; c <= GridView::dimension ; ++c)
239 sizes_[c] /= refElem.size(c);
255 template <
class Twist,
class It>
258 assert(node_ !=
nullptr);
259 const auto& gridIdSet = gridView_.grid().globalIdSet();
261 for (size_type i = 0; i < size_ ; ++i, ++it) {
262 Dune::LocalKey localKey = node_->finiteElement().localCoefficients().localKey(i);
263 unsigned int s = localKey.subEntity();
264 unsigned int c = localKey.codim();
265 it->first = {gridIdSet.subId(node_->element(), s, c), shift + twist.
get(localKey,sizes_[c])};
267 it->second = Dune::Hybrid::switchCases(std::make_index_sequence<dim+1>{}, c,
268 [&](
auto codim) {
return node_->element().template subEntity<codim>(s).partitionType(); },
270 error_exit(
"Invalid codimension c = {}", c);
271 return Dune::PartitionType{};
280 const Node* node_ =
nullptr;
282 std::array<unsigned int,GridView::dimension+1> sizes_;
287 template <
class PreBasis,
class TP>
288 class NodeIdSet<PreBasis, TP, Dune::TypeTree::PowerNodeTag>
291 using Node = Node_t<PreBasis,TP>;
292 using GridView =
typename PreBasis::GridView;
293 using size_type = std::size_t;
296 using SubPreBasis =
typename PreBasis::SubPreBasis;
297 using SubTreePath = decltype(Dune::TypeTree::push_back(std::declval<TP>(), std::size_t(0)));
299 static const std::size_t children = Node::CHILDREN;
307 void bind(
const Node& node)
310 subIds_.bind(node.child(0));
321 size_type size()
const 323 return node_->size();
327 template <
class Twist,
class It>
328 It fillIn(
Twist const& twist, It it, size_type shift = 0)
const 330 assert(node_ !=
nullptr);
331 for (std::size_t child = 0; child < children; ++child)
333 size_type subTreeSize = subIds_.size();
334 it = subIds_.fillIn(twist, it, shift);
335 shift += subTreeSize;
341 SubNodeIdSet subIds_;
342 const Node* node_ =
nullptr;
347 template <
class PreBasis,
class TP>
348 class NodeIdSet<PreBasis, TP, Dune::TypeTree::CompositeNodeTag>
351 using Node = Node_t<PreBasis,TP>;
352 using GridView =
typename PreBasis::GridView;
353 using size_type = std::size_t;
356 static const std::size_t children = Node::CHILDREN;
357 using ChildIndices = std::make_index_sequence<children>;
360 template <std::
size_t I>
361 using SubPreBasis =
typename PreBasis::template SubPreBasis<I>;
363 template <std::
size_t I>
364 using SubTreePath = decltype(Dune::TypeTree::push_back(std::declval<TP>(), Dune::index_constant<I>{}));
366 template <std::
size_t I>
370 using IdsTuple = IndexMapTuple_t<std::make_index_sequence<children>, SubNodeIdSet>;
374 : idsTuple_(Ranges::applyIndices<children>([&](
auto... i) {
375 return std::make_tuple(SubNodeIdSet<VALUE(i)>(gridView)...);
380 void bind(
const Node& node)
383 Ranges::forIndices<0,children>([&](
auto i) {
384 std::get<VALUE(i)>(idsTuple_).bind(node.child(i));
392 Ranges::forEach(idsTuple_, [](
auto& ids) {
398 size_type size()
const 400 return node_->size();
404 template <
class Twist,
class It>
405 It fillIn(
Twist const& twist, It it, size_type shift = 0)
const 407 assert(node_ !=
nullptr);
408 Ranges::forEach(idsTuple_, [&](
auto const& ids)
410 size_type subTreeSize = ids.size();
411 it = ids.fillIn(twist, it, shift);
412 shift += subTreeSize;
419 const Node* node_ =
nullptr;
423 template <
class GV,
class MI,
bool HI,
class TP>
424 class NodeIdSet<Dune::Functions::TaylorHoodPreBasis<GV,MI,HI>, TP, Dune::TypeTree::CompositeNodeTag>
427 using PreBasis = Dune::Functions::TaylorHoodPreBasis<GV,MI,HI>;
428 using Node = Node_t<PreBasis,TP>;
429 using GridView =
typename PreBasis::GridView;
430 using size_type = std::size_t;
433 using PTP = decltype(Dune::TypeTree::push_back(std::declval<TP>(), Dune::index_constant<1>{}));
434 using VTP = decltype(Dune::TypeTree::push_back(std::declval<TP>(), Dune::index_constant<0>{}));
435 using V0TP = decltype(Dune::TypeTree::push_back(std::declval<VTP>(), std::size_t(0)));
438 using PQ1PreBasis =
typename NodeIndexSet_t<PreBasis,TP>::PQ1NodeIndexSet::PreBasis;
439 using PQ2PreBasis =
typename NodeIndexSet_t<PreBasis,TP>::PQ2NodeIndexSet::PreBasis;
445 static constexpr
int dow = GridView::dimensionworld;
449 : pq1NodeIdSet_(gridView)
450 , pq2NodeIdSet_(gridView)
454 void bind(
const Node& node)
457 using namespace Dune::Indices;
458 pq1NodeIdSet_.bind(node.child(_1));
459 pq2NodeIdSet_.bind(node.child(_0, 0));
465 pq1NodeIdSet_.unbind();
466 pq2NodeIdSet_.unbind();
471 size_type size()
const 473 return node_->size();
477 template <
class Twist,
class It>
478 It fillIn(
Twist const& twist, It it, size_type shift = 0)
const 480 assert(node_ !=
nullptr);
481 for (
int child = 0; child < dow; ++child) {
482 size_type subTreeSize = pq2NodeIdSet_.size();
483 it = pq2NodeIdSet_.fillIn(twist, it, shift);
484 shift += subTreeSize;
486 it = pq1NodeIdSet_.fillIn(twist, it, shift);
491 PQ1NodeIdSet pq1NodeIdSet_;
492 PQ2NodeIdSet pq2NodeIdSet_;
493 const Node* node_ =
nullptr;
497 template <
class GV,
int k,
class MI,
class TP>
498 class NodeIdSet<Dune::Functions::LagrangeDGPreBasis<GV, k, MI>, TP>
501 using PreBasis = Dune::Functions::LagrangeDGPreBasis<GV, k, MI>;
502 using Node = Node_t<PreBasis, TP>;
503 using GridView =
typename PreBasis::GridView;
504 using size_type = std::size_t;
507 : gridView_(gridView)
511 void bind(
const Node& node)
514 size_ = node_->finiteElement().size();
524 size_type size()
const 530 template <
class Twist,
class It>
531 It fillIn(
Twist const& , It it, size_type shift = 0)
const 533 assert(node_ !=
nullptr);
534 const auto& gridIdSet = gridView_.grid().globalIdSet();
535 auto elementId = gridIdSet.id(node_->element());
537 for (size_type i = 0; i < size_; ++i, ++it)
539 it->first = {elementId, shift + i};
540 it->second = node_->element().partitionType();
548 const Node* node_ =
nullptr;
IdType id(size_type i) const
Return the global unique ID of the ith DOF on the currently bound element in the basis tree...
Definition: GlobalIdSet.hpp:164
unsigned int get(Dune::LocalKey const &localKey, unsigned int size) const
Get the permutated local dof index, living on a subEntity of the bound element.
Definition: Twist.hpp:48
Definition: AdaptiveGrid.hpp:373
Definition: FieldMatVec.hpp:12
Definition: GlobalIdSet.hpp:41
Provide global ids for all DOFs in a global basis.
Definition: GlobalIdSet.hpp:107
Definition: AdaptBase.hpp:6
Type of a global used used to represent DOFs uniquely.
Definition: GlobalIdSet.hpp:49
size_type size() const
The number of DOFs on the current element in the basis tree.
Definition: GlobalIdSet.hpp:157
void unbind()
Unbind the idset.
Definition: GlobalIdSet.hpp:243
PB PreBasis
Pre-basis providing the implementation details.
Definition: GlobalBasis.hpp:60
typename PreBasis::GridView GridView
The grid view that the FE space is defined on.
Definition: GlobalBasis.hpp:63
size_type size() const
Number of DOFs in this node.
Definition: GlobalIdSet.hpp:249
GlobalIdType & operator++()
Increment the second index only.
Definition: GlobalIdSet.hpp:61
void unbind()
unbind from the element
Definition: GlobalIdSet.hpp:151
PartitionType partitionType(size_type i) const
Return the partition type of the ith DOF on the currently bound element in the basis tree...
Definition: GlobalIdSet.hpp:179
It fillIn(Twist const &twist, It it, size_type shift=0) const
Maps from subtree index set [0..size-1] to a globally unique id in global basis.
Definition: GlobalIdSet.hpp:256
void bind(Element const &element)
Bind the IdSet to a grid element.
Definition: GlobalIdSet.hpp:141
void bind(const Node &node)
Bind the idset to a tree node.
Definition: GlobalIdSet.hpp:227
EntityIdType entityId(size_type i) const
Return the global unique ID of the entity associated to the ith DOF on the currently bound element in...
Definition: GlobalIdSet.hpp:172