LCOV - code coverage report
Current view: top level - ugbase/lib_grid - multi_grid.h (source / functions) Coverage Total Hit
Test: coverage.info Lines: 0.0 % 42 0
Test Date: 2025-09-21 23:31:46 Functions: 0.0 % 57 0

            Line data    Source code
       1              : /*
       2              :  * Copyright (c) 2009-2015:  G-CSC, Goethe University Frankfurt
       3              :  * Author: Sebastian Reiter
       4              :  * 
       5              :  * This file is part of UG4.
       6              :  * 
       7              :  * UG4 is free software: you can redistribute it and/or modify it under the
       8              :  * terms of the GNU Lesser General Public License version 3 (as published by the
       9              :  * Free Software Foundation) with the following additional attribution
      10              :  * requirements (according to LGPL/GPL v3 §7):
      11              :  * 
      12              :  * (1) The following notice must be displayed in the Appropriate Legal Notices
      13              :  * of covered and combined works: "Based on UG4 (www.ug4.org/license)".
      14              :  * 
      15              :  * (2) The following notice must be displayed at a prominent place in the
      16              :  * terminal output of covered works: "Based on UG4 (www.ug4.org/license)".
      17              :  * 
      18              :  * (3) The following bibliography is recommended for citation and must be
      19              :  * preserved in all covered files:
      20              :  * "Reiter, S., Vogel, A., Heppner, I., Rupp, M., and Wittum, G. A massively
      21              :  *   parallel geometric multigrid solver on hierarchically distributed grids.
      22              :  *   Computing and visualization in science 16, 4 (2013), 151-164"
      23              :  * "Vogel, A., Reiter, S., Rupp, M., Nägel, A., and Wittum, G. UG4 -- a novel
      24              :  *   flexible software system for simulating pde based models on high performance
      25              :  *   computers. Computing and visualization in science 16, 4 (2013), 165-179"
      26              :  * 
      27              :  * This program is distributed in the hope that it will be useful,
      28              :  * but WITHOUT ANY WARRANTY; without even the implied warranty of
      29              :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
      30              :  * GNU Lesser General Public License for more details.
      31              :  */
      32              : 
      33              : #ifndef __H__LIB_GRID__MULTI_GRID__
      34              : #define __H__LIB_GRID__MULTI_GRID__
      35              : 
      36              : #include <vector>
      37              : #include <cassert>
      38              : #include "grid/grid.h"
      39              : #include "tools/subset_handler_grid.h"
      40              : #include "common_attachments.h"
      41              : #include "common/util/array_util.h"
      42              : #include "multi_grid_child_info.h"
      43              : #include "algorithms/attachment_util.h"
      44              : 
      45              : namespace ug
      46              : {
      47              : 
      48              : ////////////////////////////////////////////////////////////////////////
      49              : /**
      50              :  * Inherits from \sa Grid.
      51              :  *
      52              :  * A MultiGrid represents a grid hierarchy. Elements in a level have a
      53              :  * parent / child relationship to elements in lower / higher levels.
      54              :  * Such a hierarchy is normally created by repeated refinement of a
      55              :  * coarse grid.
      56              :  * Enhances the Grid interface by methods that work on specific levels.
      57              :  * The MultiGrid stores all elements in one grid.
      58              :  * The hierarchy is managed by a SubsetHandler.
      59              :  * If elements are created and hierarchical insertion is activated, then
      60              :  * new elements are added one layer higher than their parents.
      61              :  * (NULL indicates base-level).
      62              :  *
      63              :  * Whenever a a level is added or removed, a message is posted at the
      64              :  * associated MessageHub (MultiGrid::message_hub()). The message has the type
      65              :  * GridMessage_MultiGridChanged (defined in "lib_grid/lib_grid_messages.h").
      66              :  * You may register a callback at the grids message-hub if you want to react
      67              :  * on such a message.
      68              :  *
      69              :  * \ingroup lib_grid_grid
      70              :  */
      71              : class MultiGrid : public Grid, public GridObserver
      72              : {
      73              :         friend struct MGVertexInfo;
      74              :         friend struct MGEdgeInfo;
      75              :         friend struct MGFaceInfo;
      76              :         friend struct MGVolumeInfo;
      77              : 
      78              :         protected:
      79              :                 typedef MGVertexInfo VertexInfo;
      80              :                 typedef MGEdgeInfo EdgeInfo;
      81              :                 typedef MGFaceInfo FaceInfo;
      82              :                 typedef MGVolumeInfo VolumeInfo;
      83              : 
      84              :         public:
      85              :                 //      methods from Grid, that would be hidden if not explicitly
      86              :                 //      declared as required.
      87              :                 using Grid::begin;
      88              :                 using Grid::end;
      89              :                 using Grid::num;
      90              :                 using Grid::get_grid_objects;
      91              :                 using Grid::create;
      92              :                 using Grid::create_by_cloning;
      93              : 
      94              : 
      95              :                 MultiGrid();
      96              :         ///     initialises the grid with the given option.
      97              :         /**     pass an or-combination of constants enumerated in
      98              :          *  VertexOptions, EdgeOptions, FaceOptions, VolumeOptions and GridOptions.*/
      99              :                 MultiGrid(uint options);
     100              :                 
     101              :                 virtual ~MultiGrid();
     102              : 
     103              :                 void enable_hierarchical_insertion(bool bEnable);
     104            0 :                 inline bool hierarchical_insertion_enabled()    {return m_bHierarchicalInsertion;}
     105              : 
     106              :         ////////////////////////////////////////////////
     107              :         //      element creation
     108              :         ///     create a custom element on a specific level.
     109              :         /**
     110              :          * TGeomObj has to be a geometric object type as described in grid_base_objects.h.
     111              :          * This method should only be used if a geometric object has to be created
     112              :          * without a parent in higher levels of the hierarchy.
     113              :          * Use the create method derived from ug::Grid if you want to specify a parent.
     114              :          * \{ */
     115              :                 template<class TGeomObj>
     116              :                 typename geometry_traits<TGeomObj>::iterator
     117              :                 create(size_t level);
     118              : 
     119              :                 template <class TGeomObj>
     120              :                 typename geometry_traits<TGeomObj>::iterator
     121              :                 create(const typename geometry_traits<TGeomObj>::Descriptor& descriptor,
     122              :                                 size_t level);
     123              :         /**     \} */
     124              : 
     125              :         ///     this method creates a new vertex, which has the same type as pCloneMe.
     126              :                 VertexIterator create_by_cloning(Vertex* pCloneMe,
     127              :                                                                                         int level);
     128              : 
     129              :         ///     this method creates a new edge, which has the same type as pCloneMe.
     130              :                 EdgeIterator create_by_cloning(Edge* pCloneMe,
     131              :                                                                                    const EdgeVertices& ev,
     132              :                                                                                    int level);
     133              : 
     134              :         ///     this method creates a new face, which has the same type as pCloneMe.
     135              :                 FaceIterator create_by_cloning(Face* pCloneMe,
     136              :                                                                            const FaceVertices& fv,
     137              :                                                                            int level);
     138              : 
     139              :         ///     this method creates a new volume, which has the same type as pCloneMe.
     140              :                 VolumeIterator create_by_cloning(Volume* pCloneMe,
     141              :                                                                                  const VolumeVertices& vv,
     142              :                                                                                  int level);
     143              : 
     144              :         ///     number of levels
     145            0 :                 inline size_t num_levels() const        {return (size_t)m_hierarchy.num_subsets();}
     146              : 
     147              :         ///     index of the highest level.
     148              :                 inline size_t top_level() const;
     149              : 
     150              :         ///     creates new (empty) levels until num_levels() == lvl+1
     151              :                 inline void level_required(int lvl);
     152              : 
     153              :                 template <class TElem> inline
     154            0 :                 size_t num(int level) const             {return m_hierarchy.num<TElem>(level);}
     155              : 
     156              :                 template <class TElem> inline
     157              :                 typename geometry_traits<TElem>::iterator
     158            0 :                 begin(int level)
     159              :                 {
     160              :                         //assert(level < (int)num_levels() && "ERROR in MultiGrid::begin(...): requested level too high!");
     161            0 :                         if(level >= (int)num_levels())
     162              :                                 return end<TElem>();
     163            0 :                         return m_hierarchy.begin<TElem>(level);
     164              :                 }
     165              : 
     166              :                 template <class TElem> inline
     167              :                 typename geometry_traits<TElem>::iterator
     168            0 :                 end(int level)
     169              :                 {
     170              :                         //assert(level < (int)num_levels() && "ERROR in MultiGrid::end(...): requested level too high!");
     171            0 :                         if(level >= (int)num_levels())
     172              :                                 return end<TElem>();
     173            0 :                         return m_hierarchy.end<TElem>(level);
     174              :                 }
     175              : 
     176              :                 template <class TElem> inline
     177              :                 typename geometry_traits<TElem>::const_iterator
     178            0 :                 begin(int level) const
     179              :                 {
     180              :                         //assert(level < (int)num_levels() && "ERROR in MultiGrid::begin(...): requested level too high!");
     181            0 :                         if(level >= (int)num_levels())
     182              :                                 return end<TElem>();
     183            0 :                         return m_hierarchy.begin<TElem>(level);
     184              :                 }
     185              : 
     186              :                 template <class TElem> inline
     187              :                 typename geometry_traits<TElem>::const_iterator
     188            0 :                 end(int level) const
     189              :                 {
     190              :                         //assert(level < (int)num_levels() && "ERROR in MultiGrid::end(...): requested level too high!");
     191            0 :                         if(level >= (int)num_levels())
     192              :                                 return end<TElem>();
     193            0 :                         return m_hierarchy.end<TElem>(level);
     194              :                 }
     195              : 
     196              :         //      geometric-object-collection
     197              :                 inline GridObjectCollection
     198              :                 get_grid_objects(int level)
     199            0 :                 {return m_hierarchy.get_grid_objects_in_subset(level);}
     200              :                 
     201              :         //      multi-level-geometric-object-collection
     202            0 :                 virtual GridObjectCollection get_grid_objects()
     203            0 :                 {return m_hierarchy.get_grid_objects();}
     204              :                 
     205              :                 template <class TElem> inline
     206              :                 int get_level(TElem* elem) const
     207            0 :                 {return m_hierarchy.get_subset_index(elem);}
     208              : 
     209              :                 GridObject* get_parent(GridObject* parent) const;
     210            0 :                 inline GridObject* get_parent(Vertex* o) const  {return get_info(o).m_pParent;}
     211            0 :                 inline GridObject* get_parent(Edge* o) const    {return get_info(o).m_pParent;}
     212            0 :                 inline GridObject* get_parent(Face* o) const            {return m_aaParentFACE[o];}
     213            0 :                 inline GridObject* get_parent(Volume* o) const          {return m_aaParentVOL[o];}
     214              : 
     215              :         //      number of children
     216              :                 template <class TElem> inline
     217            0 :                 bool has_children(TElem* elem) const
     218            0 :                 {return get_info(elem).has_children();}
     219              : 
     220              :         ////////////////////////////////
     221              :         //      CHILD QUANTITIES
     222              :         ///     returns the number of children of the given child-type
     223              :         /** \{ */
     224              :                 template <class TChild, class TElem>
     225              :                 inline size_t num_children(TElem* elem) const   {return num_children(elem, TChild());}
     226              : 
     227              :                 template <class TChild>
     228              :                 size_t num_children(GridObject* elem)   const;
     229              :         /** \} */
     230              : 
     231              :         ///     returns the total number of children and grand-children.
     232              :         /**     Only children of the same type as the given elements are regarded here.*/
     233              :                 template <class TElem>
     234              :                 inline size_t num_children_total(TElem* elem)   const;
     235              : 
     236              :         ///     Returns the number of child vertices
     237              :                 template <class TElem>
     238            0 :                 inline size_t num_child_vertices(TElem* elem) const     {return get_info(elem).num_child_vertices();}
     239              : 
     240              :         ///     Returns the number of child edges
     241              :         /**     \{      */
     242              :                 template <class TElem>
     243            0 :                 inline size_t num_child_edges(TElem* elem) const        {return get_info(elem).num_child_edges();}
     244              :                 inline size_t num_child_edges(Vertex*) const    {return 0;}
     245              :         /**     \}      */
     246              : 
     247              :         ///     Returns the number of child faces
     248              :         /**     \{      */
     249              :                 template <class TElem>
     250            0 :                 inline size_t num_child_faces(TElem* elem) const        {return get_info(elem).num_child_faces();}
     251              :                 inline size_t num_child_faces(Vertex*) const    {return 0;}
     252              :                 inline size_t num_child_faces(Edge*) const              {return 0;}
     253              :         /**     \}      */
     254              : 
     255              :         ///     Returns the number of child volumes
     256              :         /**     \{      */
     257            0 :                 inline size_t num_child_volumes(Volume* elem) const     {return get_info(elem).num_child_volumes();}
     258              :                 template <class TElem>
     259              :                 inline size_t num_child_volumes(TElem*) const           {return 0;}
     260              :         /**     \}      */
     261              : 
     262              : 
     263              :         ////////////////////////////////
     264              :         //      CHILD ACCESS
     265              :         ///     returns the i-th child of the given child-type
     266              :         /** \{ */
     267              :                 template <class TChild, class TElem>
     268              :                 inline TChild* get_child(TElem* elem, size_t ind) const {return get_child(elem, ind, TChild());}
     269              : 
     270              :                 template <class TChild>
     271              :                 TChild* get_child(GridObject* elem, size_t ind) const;
     272              :         /** \} */
     273              : 
     274              :         ///     Returns the child vertex of the given element or NULL if there is none
     275              :                 template <class TElem>
     276            0 :                 inline Vertex* get_child_vertex(TElem* elem) const      {return get_info(elem).child_vertex();}
     277              : 
     278              :         ///     Returns the child edges of the given element or NULL if there is none
     279              :         /**     \{      */
     280              :                 template <class TElem>
     281            0 :                 inline Edge* get_child_edge(TElem* elem, size_t ind) const      {return get_info(elem).child_edge(ind);}
     282              :                 inline Edge* get_child_edge(Vertex*, size_t) const              {return NULL;}
     283              :         /**     \}      */
     284              : 
     285              :         ///     Returns the child faces of the given element or NULL if there is none
     286              :         /**     \{      */
     287              :                 template <class TElem>
     288            0 :                 inline Face* get_child_face(TElem* elem, size_t ind) const      {return get_info(elem).child_face(ind);}
     289              :                 inline Face* get_child_face(Vertex*, size_t) const              {return NULL;}
     290              :                 inline Face* get_child_face(Edge*, size_t) const                        {return NULL;}
     291              :         /**     \}      */
     292              : 
     293              :         ///     Returns the child volumes of the given element or NULL if there is none
     294              :         /**     \{      */
     295            0 :                 inline Volume* get_child_volume(Volume* elem, size_t ind) const {return get_info(elem).child_volume(ind);}
     296              :                 template <class TElem>
     297              :                 inline Volume* get_child_volume(TElem*, size_t) const   {return NULL;}
     298              :         /**     \}      */
     299              : 
     300              :         ///     clears the relation between a parent and its children
     301              :         /**     Use with care. This method should only be called if no other option exists.*/
     302              :                 template <class TElem>
     303              :                 void clear_child_connections(TElem* parent);
     304              : 
     305              :         ///     establishes a parent child connection between the given elements
     306              :         /**     Note that the MultGrid class automatically establishes a parent child
     307              :          * connection during element creation, based on the suppliend parent argument.
     308              :          * This method should thus only be used in the rare cases where this
     309              :          * automatic association is not sufficient.
     310              :          * Note that only elements of equal or higher dimension can be parent to a
     311              :          * given element.
     312              :          * Note that while parent may be NULL, elem has to be supplied.
     313              :          * The method also sets the parent type if a parent is supplied and leaves the
     314              :          * parent type as it is if none is supplied.*/
     315              :                 template <class TElem>
     316              :                 void associate_parent(TElem* elem, GridObject* parent);
     317              : 
     318              :         ///     returns the object-type of the parent of a given object
     319              :                 template <class TElem>
     320              :                 char parent_type(TElem* elem) const;
     321              : 
     322              :         ///     sets the object-type of the parent of a given object
     323              :         /**     The parent type is normally handled internally. However, e.g. during
     324              :          * parallel redistribution it may have to be set from outside (e.g. if
     325              :          * a parent element hasn't been transfered to the same process as its children).*/
     326              :                 template <class TElem>
     327              :                 void set_parent_type(TElem* elem, char type);
     328              : 
     329              :         ///     for debug purposes
     330              :                 void check_edge_elem_infos(int level) const;
     331              :         ///     for debug purposes
     332              :                 void check_face_elem_infos(int level) const;
     333              :         ///     for debug purposes
     334              :                 void check_volume_elem_infos(int level) const;
     335              :                 
     336              :         ///     this method may be removed in future versions of the MultiGrid-class.
     337              :         /**     You really shouldn't use this method!!!*/
     338              :                 SubsetHandler& get_hierarchy_handler()              {return m_hierarchy;}
     339              :                 
     340              :         ////////////////////////////////////////////////////////////////////////
     341              :         //      Don't invoke the following methods directly!
     342              :         //      They are intended for internal feedback only.
     343              : 
     344              :         //      grid callbacks
     345              :                 virtual void elements_to_be_cleared(Grid* grid);
     346              : 
     347              :          /**  In order to correctly register vrt in the hierarchy, we have to
     348              :          *  replace pParent with vrt in the list of children of pParents parent.
     349              :          *  This means that if a grid-observer registered after the multi-grid itself,
     350              :          *  iterates over the list of children of pParents parent in its
     351              :          *  vertex_created method, it won't find pParent.*/
     352              :                 virtual void vertex_created(Grid* grid, Vertex* vrt,
     353              :                                                                         GridObject* pParent = NULL,
     354              :                                                                         bool replacesParent = false);
     355              : 
     356              :          /**  In order to correctly register e in the hierarchy, we have to
     357              :          *  replace pParent with e in the list of children of pParents parent.
     358              :          *  This means that if a grid-observer registered after the multi-grid itself,
     359              :          *  iterates over the list of children of pParents parent in its
     360              :          *  edge_created method, it won't find pParent.*/
     361              :                 virtual void edge_created(Grid* grid, Edge* e,
     362              :                                                                         GridObject* pParent = NULL,
     363              :                                                                         bool replacesParent = false);
     364              : 
     365              :          /**  In order to correctly register f in the hierarchy, we have to
     366              :          *  replace pParent with f in the list of children of pParents parent.
     367              :          *  This means that if a grid-observer registered after the multi-grid itself,
     368              :          *  iterates over the list of children of pParents parent in its
     369              :          *  face_created method, it won't find pParent.*/
     370              :                 virtual void face_created(Grid* grid, Face* f,
     371              :                                                                         GridObject* pParent = NULL,
     372              :                                                                         bool replacesParent = false);
     373              : 
     374              :          /**  In order to correctly register vol in the hierarchy, we have to
     375              :          *  replace pParent with vol in the list of children of pParents parent.
     376              :          *  This means that if a grid-observer registered after the multi-grid itself,
     377              :          *  iterates over the list of children of pParents parent in its
     378              :          *  volume_created method, it won't find pParent.*/
     379              :                 virtual void volume_created(Grid* grid, Volume* vol,
     380              :                                                                         GridObject* pParent = NULL,
     381              :                                                                         bool replacesParent = false);
     382              : 
     383              :                 virtual void vertex_to_be_erased(Grid* grid, Vertex* vrt,
     384              :                                                                                  Vertex* replacedBy = NULL);
     385              : 
     386              :                 virtual void edge_to_be_erased(Grid* grid, Edge* e,
     387              :                                                                                  Edge* replacedBy = NULL);
     388              : 
     389              :                 virtual void face_to_be_erased(Grid* grid, Face* f,
     390              :                                                                                  Face* replacedBy = NULL);
     391              : 
     392              :                 virtual void volume_to_be_erased(Grid* grid, Volume* vol,
     393              :                                                                                  Volume* replacedBy = NULL);
     394              : 
     395              :         protected:
     396              : 
     397              :         //      Note: VertexInfo and EdgeInfo are stored directly, FaceInfo and
     398              :         //      VolumeInfo are stored dynamically.
     399              :                 typedef Attachment<GridObject*>   AParent;
     400              :                 typedef Attachment<VertexInfo>                    AVertexInfo;
     401              :                 typedef Attachment<EdgeInfo>                      AEdgeInfo;
     402              :                 typedef Attachment<FaceInfo*>                     AFaceInfo;
     403              :                 typedef Attachment<VolumeInfo*>                   AVolumeInfo;
     404              :                 typedef Attachment<char>                          AParentType;
     405              : 
     406              : 
     407              :         //      initialization
     408              :                 void init();
     409              :                 
     410              :         //      create levels
     411              :                 void create_levels(int numLevels);
     412              : 
     413              :         //      info-access
     414              :                 inline VertexInfo& get_info(Vertex* v);
     415              :                 inline EdgeInfo& get_info(Edge* e);
     416              :                 inline FaceInfo& get_info(Face* f);
     417              :                 inline VolumeInfo& get_info(Volume* v);
     418              : 
     419              :         //      const info-access
     420              :                 inline const VertexInfo& get_info(Vertex* v) const;
     421              :                 inline const EdgeInfo& get_info(Edge* e) const;
     422              :                 inline const FaceInfo& get_info(Face* f) const;
     423              :                 inline const VolumeInfo& get_info(Volume* v) const;
     424              : 
     425              :         //      elem creation
     426              :                 template <class TElem>
     427            0 :                 inline void element_created(TElem* elem)        {element_created<TElem, TElem>(elem, NULL);}
     428              : 
     429              :                 template <class TElem, class TParent>
     430              :                 void element_created(TElem* elem, TParent* pParent);
     431              : 
     432              :         ///     called if a newly created element shall replace an old one
     433              :                 template <class TElem, class TParent>
     434              :                 void element_created(TElem* elem, TParent* pParent, TElem* pReplaceMe);
     435              : 
     436              :         ///     this method is called for elements that havn't got any parent.
     437              :                 template <class TElem>
     438              :                 void element_to_be_erased(TElem* elem);
     439              : 
     440              :         ///     this method is called for elements with a parent.
     441              :                 template <class TElem, class TParent>
     442              :                 void element_to_be_erased(TElem* elem, TParent* pParent);
     443              : 
     444              :                 //template <class TElem>
     445              :                 //void element_to_be_replaced(TElem* elemOld, TElem* elemNew);
     446              : 
     447              : 
     448              :         ///     returning the number of children of the type of the dummy-argument.
     449              :         /**     \{ */
     450              :                 template <class TElem>
     451              :                 inline size_t num_children(TElem* elem, const Vertex&) const
     452              :                         {return num_child_vertices(elem);}
     453              : 
     454              :                 template <class TElem>
     455              :                 inline size_t num_children(TElem* elem, const Edge&) const
     456              :                         {return num_child_edges(elem);}
     457              : 
     458              :                 template <class TElem>
     459              :                 inline size_t num_children(TElem* elem, const Face&) const
     460              :                         {return num_child_faces(elem);}
     461              : 
     462              :                 template <class TElem>
     463              :                 inline size_t num_children(TElem* elem, const Volume&) const
     464              :                         {return num_child_volumes(elem);}
     465              :         /**     \} */
     466              : 
     467              :         ///     returning the i-th child of the type of the dummy-argument.
     468              :         /**     \{ */
     469              :                 template <class TElem>
     470              :                 inline Vertex* get_child(TElem* elem, size_t ind, const Vertex&) const
     471              :                         {return get_child_vertex(elem);}
     472              : 
     473              :                 template <class TElem>
     474              :                 inline Edge* get_child(TElem* elem, size_t ind, const Edge&) const
     475              :                         {return get_child_edge(elem, ind);}
     476              : 
     477              :                 template <class TElem>
     478              :                 inline Face* get_child(TElem* elem, size_t ind, const Face&) const
     479              :                         {return get_child_face(elem, ind);}
     480              : 
     481              :                 template <class TElem>
     482              :                 inline Volume* get_child(TElem* elem, size_t ind, const Volume&) const
     483              :                         {return get_child_volume(elem, ind);}
     484              :         /**     \} */
     485              : 
     486              :         ///     sets the parent for the given object
     487              :         /**     \{ */
     488            0 :                 inline void set_parent(Vertex* o, GridObject* p)        {get_info(o).m_pParent = p;}
     489            0 :                 inline void set_parent(Edge* o, GridObject* p)          {get_info(o).m_pParent = p;}
     490            0 :                 inline void set_parent(Face* o, GridObject* p)                  {m_aaParentFACE[o] = p;}
     491            0 :                 inline void set_parent(Volume* o, GridObject* p)                {m_aaParentVOL[o] = p;}
     492              :         /**     \} */
     493              : 
     494              :         ///     adds a child to the given object
     495              :         /** \{ */
     496              :                 template <class TParent, class TChild>
     497              :                 void add_child(TParent* p, TChild* c);
     498              : 
     499              :                 template <class TChild>
     500              :                 void add_child(GridObject* p, TChild* c);
     501              :         /** \} */
     502              : 
     503              :         ///     removes a child from the given object
     504              :         /** \{ */
     505              :                 template <class TParent, class TChild>
     506              :                 void remove_child(TParent* p, TChild* c);
     507              : 
     508              :                 template <class TChild>
     509              :                 void remove_child(GridObject* p, TChild* c);
     510              :         /** \} */
     511              : 
     512              :         ///     creates the info-object for the given object (if necessary)
     513              :         /**     \{ */
     514              :                 inline void create_child_info(Vertex* o){}
     515              :                 inline void create_child_info(Edge* o)  {}
     516            0 :                 inline void create_child_info(Face* o)          {if(!m_aaFaceInf[o]) m_aaFaceInf[o] = new FaceInfo();}
     517            0 :                 inline void create_child_info(Volume* o)        {if(!m_aaVolInf[o]) m_aaVolInf[o] = new VolumeInfo();}
     518              :         /**     \} */
     519              : 
     520              :         ///     releases the info-object for the given object (if necessary)
     521              :         /**     \{ */
     522              :                 inline void release_child_info(Vertex* o)       {}
     523              :                 inline void release_child_info(Edge* o)         {}
     524            0 :                 inline void release_child_info(Face* o)                 {if(m_aaFaceInf[o]) delete m_aaFaceInf[o]; m_aaFaceInf[o] = NULL;}
     525            0 :                 inline void release_child_info(Volume* o)               {if(m_aaVolInf[o]) delete m_aaVolInf[o]; m_aaVolInf[o] = NULL;}
     526              :         /**     \} */
     527              : 
     528              : 
     529              :         //      hierarchy
     530              :                 SubsetHandler   m_hierarchy;
     531              :                 bool m_bHierarchicalInsertion;
     532              : 
     533              :         //      parent attachment
     534              :                 AParent         m_aParent;
     535              : 
     536              :         //      info attachments
     537              :                 AVertexInfo     m_aVertexInfo;
     538              :                 AEdgeInfo       m_aEdgeInfo;
     539              :                 AFaceInfo       m_aFaceInfo;
     540              :                 AVolumeInfo     m_aVolumeInfo;
     541              :                 AParentType     m_aParentType;
     542              : 
     543              :         //      parent access - only required for faces and volumes.
     544              :                 Grid::FaceAttachmentAccessor<AParent>             m_aaParentFACE;
     545              :                 Grid::VolumeAttachmentAccessor<AParent>           m_aaParentVOL;
     546              : 
     547              :         //      element info access
     548              :                 Grid::VertexAttachmentAccessor<AVertexInfo>       m_aaVrtInf;
     549              :                 Grid::EdgeAttachmentAccessor<AEdgeInfo>           m_aaEdgeInf;
     550              :                 Grid::FaceAttachmentAccessor<AFaceInfo>           m_aaFaceInf;
     551              :                 Grid::VolumeAttachmentAccessor<AVolumeInfo>       m_aaVolInf;
     552              : 
     553              :                 MultiElementAttachmentAccessor<AParentType>       m_aaParentType;
     554              : };
     555              : 
     556              : 
     557              : 
     558              : ////////////////////////////////////////////////////////////////////////
     559              : ////////////////////////////////////////////////////////////////////////
     560              : ///     wrapper that allows to write method that can operate on a ug::Grid and a ug::MultiGrid.
     561              : /**
     562              :  * This template class is specialized for ug::Grid and ug::MultiGrid.
     563              :  *
     564              :  * The MGWrapper will most likely be enhanced with more mg-methods, like
     565              :  * has_child, get_child or parent.
     566              :  */
     567              : template <class TGrid>
     568              : class MGWrapper
     569              : {
     570              :         public:
     571              :                 MGWrapper(TGrid& grid);
     572              :                 
     573              :                 inline uint num_levels() const;
     574              : 
     575              :                 template <class TElem> inline
     576              :                 uint num(int level) const;
     577              : 
     578              :                 template <class TElem> inline
     579              :                 typename geometry_traits<TElem>::iterator
     580              :                 begin(int level);
     581              : 
     582              :                 template <class TElem> inline
     583              :                 typename geometry_traits<TElem>::iterator
     584              :                 end(int level);
     585              : };
     586              : 
     587              : }//     end of namespace
     588              : 
     589              : ////////////////////////////////
     590              : //      include implementation
     591              : #include "multi_grid_impl.hpp"
     592              : 
     593              : #endif
        

Generated by: LCOV version 2.0-1