Reference documentation for deal.II version 8.4.2
tria_objects.h
1 // ---------------------------------------------------------------------
2 //
3 // Copyright (C) 2006 - 2015 by the deal.II authors
4 //
5 // This file is part of the deal.II library.
6 //
7 // The deal.II library is free software; you can use it, redistribute
8 // it, and/or modify it under the terms of the GNU Lesser General
9 // Public License as published by the Free Software Foundation; either
10 // version 2.1 of the License, or (at your option) any later version.
11 // The full text of the license can be found in the file LICENSE at
12 // the top level of the deal.II distribution.
13 //
14 // ---------------------------------------------------------------------
15 
16 #ifndef dealii__tria_objects_h
17 #define dealii__tria_objects_h
18 
19 #include <deal.II/base/config.h>
20 #include <deal.II/base/exceptions.h>
21 #include <deal.II/base/geometry_info.h>
22 #include <deal.II/grid/tria_object.h>
23 
24 #include <vector>
25 
26 DEAL_II_NAMESPACE_OPEN
27 
28 //TODO: This should all be cleaned up. Currently, only a single
29 //function in the library makes use of the odd specializations, and
30 //this function is Triangulation::execute_refinement() in 3D. I
31 //assume, that the other refinement functions would profit from using
32 //next_free_single_object() and next_free_pair_object, but they seem
33 //to get around it.
34 
35 //TODO: The TriaObjects class contains a std::vector<G>. This is only an
36 //efficient storage scheme if G is relatively well packed, i.e. it's not a
37 //bool and then an integer and then a double, etc. Verify that this is
38 //actually the case.
39 
40 template <int dim, int spacedim> class Triangulation;
41 template <class Accessor> class TriaRawIterator;
42 template <int, int, int> class TriaAccessor;
43 
44 namespace internal
45 {
46  namespace Triangulation
47  {
48 
61  template <typename G>
62  class TriaObjects
63  {
64  public:
68  TriaObjects();
69 
74  std::vector<G> cells;
75 
87  std::vector<int> children;
88 
94  std::vector<RefinementCase<G::dimension> > refinement_cases;
95 
104  std::vector<bool> used;
105 
115  std::vector<bool> user_flags;
116 
117 
123  {
124  union
125  {
126  types::boundary_id boundary_id;
127  types::material_id material_id;
128  };
129 
130 
135 
139  static
140  std::size_t memory_consumption ();
141 
146  template <class Archive>
147  void serialize(Archive &ar,
148  const unsigned int version);
149  };
150 
165  std::vector<BoundaryOrMaterialId> boundary_or_material_id;
166 
171  std::vector<types::manifold_id> manifold_id;
172 
183  void reserve_space (const unsigned int new_objs_in_pairs,
184  const unsigned int new_objs_single = 0);
185 
197  template <int dim, int spacedim>
199  next_free_single_object (const ::Triangulation<dim,spacedim> &tria);
200 
212  template <int dim, int spacedim>
214  next_free_pair_object (const ::Triangulation<dim,spacedim> &tria);
215 
220  template <int dim, int spacedim>
221  typename ::Triangulation<dim,spacedim>::raw_hex_iterator
222  next_free_hex (const ::Triangulation<dim,spacedim> &tria,
223  const unsigned int level);
224 
228  void clear();
229 
244  bool face_orientation(const unsigned int cell, const unsigned int face) const;
245 
246 
250  void *&user_pointer(const unsigned int i);
251 
255  const void *user_pointer(const unsigned int i) const;
256 
260  unsigned int &user_index(const unsigned int i);
261 
265  unsigned int user_index(const unsigned int i) const;
266 
270  void clear_user_data(const unsigned int i);
271 
276  void clear_user_data();
277 
281  void clear_user_flags();
282 
288  void monitor_memory (const unsigned int true_dimension) const;
289 
294  std::size_t memory_consumption () const;
295 
300  template <class Archive>
301  void serialize(Archive &ar,
302  const unsigned int version);
303 
307  DeclException3 (ExcMemoryWasted,
308  char *, int, int,
309  << "The container " << arg1 << " contains "
310  << arg2 << " elements, but it`s capacity is "
311  << arg3 << ".");
316  DeclException2 (ExcMemoryInexact,
317  int, int,
318  << "The containers have sizes " << arg1 << " and "
319  << arg2 << ", which is not as expected.");
320 
324  DeclException2 (ExcWrongIterator,
325  char *, char *,
326  << "You asked for the next free " << arg1 << "_iterator, "
327  "but you can only ask for " << arg2 <<"_iterators.");
328 
336  DeclException0 (ExcPointerIndexClash);
337 
338  protected:
342  unsigned int next_free_single;
343 
347  unsigned int next_free_pair;
348 
353 
357  struct UserData
358  {
359  union
360  {
363  void *p;
366  unsigned int i;
367  };
368 
373  {
374  p = 0;
375  }
376 
381  template <class Archive>
382  void serialize (Archive &ar, const unsigned int version);
383  };
384 
389  {
396  };
397 
398 
403  std::vector<UserData> user_data;
404 
411  };
412 
419  class TriaObjectsHex : public TriaObjects<TriaObject<3> >
420  {
421  public:
429  bool face_orientation(const unsigned int cell, const unsigned int face) const;
430 
431 
452  std::vector<bool> face_orientations;
453 
457  std::vector<bool> face_flips;
458 
462  std::vector<bool> face_rotations;
463 
470  void reserve_space (const unsigned int new_objs);
471 
475  void clear();
476 
482  void monitor_memory (const unsigned int true_dimension) const;
483 
488  std::size_t memory_consumption () const;
489 
494  template <class Archive>
495  void serialize(Archive &ar,
496  const unsigned int version);
497  };
498 
499 
506  class TriaObjectsQuad3D: public TriaObjects<TriaObject<2> >
507  {
508  public:
516  bool face_orientation(const unsigned int cell, const unsigned int face) const;
517 
518 
523  std::vector<bool> line_orientations;
524 
532  void reserve_space (const unsigned int new_quads_in_pairs,
533  const unsigned int new_quads_single = 0);
534 
538  void clear();
539 
545  void monitor_memory (const unsigned int true_dimension) const;
546 
551  std::size_t memory_consumption () const;
552 
557  template <class Archive>
558  void serialize(Archive &ar,
559  const unsigned int version);
560  };
561 
562 //----------------------------------------------------------------------//
563 
564 
565  template <typename G>
566  inline
568  {
569  material_id = numbers::invalid_material_id;
570  }
571 
572 
573 
574  template <typename G>
575  std::size_t
577  {
578  return sizeof(BoundaryOrMaterialId);
579  }
580 
581 
582 
583  template <typename G>
584  template <class Archive>
585  void
587  const unsigned int /*version*/)
588  {
589  // serialize this
590  // structure by
591  // writing and
592  // reading the larger
593  // of the two values,
594  // in order to make
595  // sure we get all
596  // bits
597  if (sizeof(material_id) > sizeof(boundary_id))
598  ar &material_id;
599  else
600  ar &boundary_id;
601  }
602 
603 
604  template<typename G>
605  inline
606  bool
608  face_orientation(const unsigned int, const unsigned int) const
609  {
610  return true;
611  }
612 
613 
614  template<typename G>
615  inline
616  void *&
617  TriaObjects<G>::user_pointer (const unsigned int i)
618  {
620  ExcPointerIndexClash());
622 
623  Assert(i<user_data.size(), ExcIndexRange(i,0,user_data.size()));
624  return user_data[i].p;
625  }
626 
627 
628  template<typename G>
629  inline
630  const void *
631  TriaObjects<G>::user_pointer (const unsigned int i) const
632  {
634  ExcPointerIndexClash());
636 
637  Assert(i<user_data.size(), ExcIndexRange(i,0,user_data.size()));
638  return user_data[i].p;
639  }
640 
641 
642  template<typename G>
643  inline
644  unsigned int &
645  TriaObjects<G>::user_index (const unsigned int i)
646  {
648  ExcPointerIndexClash());
650 
651  Assert(i<user_data.size(), ExcIndexRange(i,0,user_data.size()));
652  return user_data[i].i;
653  }
654 
655 
656  template<typename G>
657  inline
658  void
659  TriaObjects<G>::clear_user_data (const unsigned int i)
660  {
661  Assert(i<user_data.size(), ExcIndexRange(i,0,user_data.size()));
662  user_data[i].i = 0;
663  }
664 
665 
666  template <typename G>
667  inline
669  :
672  {}
673 
674 
675  template<typename G>
676  inline
677  unsigned int TriaObjects<G>::user_index (const unsigned int i) const
678  {
679  Assert(user_data_type == data_unknown || user_data_type == data_index,
680  ExcPointerIndexClash());
681  user_data_type = data_index;
682 
683  Assert(i<user_data.size(), ExcIndexRange(i,0,user_data.size()));
684  return user_data[i].i;
685  }
686 
687 
688  template<typename G>
689  inline
691  {
692  user_data_type = data_unknown;
693  for (unsigned int i=0; i<user_data.size(); ++i)
694  user_data[i].p = 0;
695  }
696 
697 
698  template<typename G>
699  inline
701  {
702  user_flags.assign(user_flags.size(),false);
703  }
704 
705 
706  template<typename G>
707  template <class Archive>
708  void
710  const unsigned int)
711  {
712  // serialize this as an integer
713  ar &i;
714  }
715 
716 
717 
718  template <typename G>
719  template <class Archive>
720  void TriaObjects<G>::serialize(Archive &ar,
721  const unsigned int)
722  {
723  ar &cells &children;
724  ar &refinement_cases;
725  ar &used;
726  ar &user_flags;
727  ar &boundary_or_material_id;
728  ar &manifold_id;
729  ar &next_free_single &next_free_pair &reverse_order_next_free_single;
730  ar &user_data &user_data_type;
731  }
732 
733 
734  template <class Archive>
735  void TriaObjectsHex::serialize(Archive &ar,
736  const unsigned int version)
737  {
738  this->TriaObjects<TriaObject<3> >::serialize (ar, version);
739 
740  ar &face_orientations &face_flips &face_rotations;
741  }
742 
743 
744  template <class Archive>
745  void TriaObjectsQuad3D::serialize(Archive &ar,
746  const unsigned int version)
747  {
748  this->TriaObjects<TriaObject<2> >::serialize (ar, version);
749 
750  ar &line_orientations;
751  }
752 
753 
754 //----------------------------------------------------------------------//
755 
756  inline
757  bool
758  TriaObjectsHex::face_orientation(const unsigned int cell,
759  const unsigned int face) const
760  {
761  Assert (cell < face_orientations.size() / GeometryInfo<3>::faces_per_cell,
762  ExcIndexRange(0, cell, face_orientations.size() / GeometryInfo<3>::faces_per_cell));
764  ExcIndexRange(0, face, GeometryInfo<3>::faces_per_cell));
765 
766  return face_orientations[cell * GeometryInfo<3>::faces_per_cell
767  + face];
768  }
769 
770 //----------------------------------------------------------------------//
771 
772  inline
773  bool
774  TriaObjectsQuad3D::face_orientation(const unsigned int cell, const unsigned int face) const
775  {
776  return line_orientations[cell * GeometryInfo<2>::faces_per_cell
777  + face];
778  }
779 
780 
781 //----------------------------------------------------------------------//
782 
783  template <class G>
784  template <int dim, int spacedim>
786  TriaObjects<G>::next_free_single_object (const ::Triangulation<dim,spacedim> &tria)
787  {
788  // TODO: Think of a way to ensure that we are using the correct triangulation, i.e. the one containing *this.
789 
790  int pos=next_free_single,
791  last=used.size()-1;
792  if (!reverse_order_next_free_single)
793  {
794  // first sweep forward, only use really single slots, do not use
795  // pair slots
796  for (; pos<last; ++pos)
797  if (!used[pos])
798  if (used[++pos])
799  {
800  // this was a single slot
801  pos-=1;
802  break;
803  }
804  if (pos>=last)
805  {
806  reverse_order_next_free_single=true;
807  next_free_single=used.size()-1;
808  pos=used.size()-1;
809  }
810  else
811  next_free_single=pos+1;
812  }
813 
814  if (reverse_order_next_free_single)
815  {
816  // second sweep, use all slots, even
817  // in pairs
818  for (; pos>=0; --pos)
819  if (!used[pos])
820  break;
821  if (pos>0)
822  next_free_single=pos-1;
823  else
824  // no valid single object anymore
825  return ::TriaRawIterator<::TriaAccessor<G::dimension,dim,spacedim> >(&tria, -1, -1);
826  }
827 
828  return ::TriaRawIterator<::TriaAccessor<G::dimension,dim,spacedim> >(&tria, 0, pos);
829  }
830 
831 
832 
833  template <class G>
834  template <int dim, int spacedim>
836  TriaObjects<G>::next_free_pair_object (const ::Triangulation<dim,spacedim> &tria)
837  {
838  // TODO: Think of a way to ensure that we are using the correct triangulation, i.e. the one containing *this.
839 
840  int pos=next_free_pair,
841  last=used.size()-1;
842  for (; pos<last; ++pos)
843  if (!used[pos])
844  if (!used[++pos])
845  {
846  // this was a pair slot
847  pos-=1;
848  break;
849  }
850  if (pos>=last)
851  // no free slot
852  return ::TriaRawIterator<::TriaAccessor<G::dimension,dim,spacedim> >(&tria, -1, -1);
853  else
854  next_free_pair=pos+2;
855 
856  return ::TriaRawIterator<::TriaAccessor<G::dimension,dim,spacedim> >(&tria, 0, pos);
857  }
858 
859 
860 
861 // declaration of explicit specializations
862 
863  template<>
864  void
865  TriaObjects<TriaObject<2> >::monitor_memory (const unsigned int) const;
866 
867  }
868 }
869 
870 
871 
872 DEAL_II_NAMESPACE_CLOSE
873 
874 #endif
std::vector< UserData > user_data
Definition: tria_objects.h:403
DeclException3(ExcMemoryWasted, char *, int, int,<< "The container "<< arg1<< " contains "<< arg2<< " elements, but it`s capacity is "<< arg3<< ".")
DeclException0(ExcPointerIndexClash)
unsigned char material_id
Definition: types.h:130
void serialize(Archive &ar, const unsigned int version)
Definition: tria_objects.h:586
unsigned int & user_index(const unsigned int i)
Definition: tria_objects.h:645
DeclException2(ExcMemoryInexact, int, int,<< "The containers have sizes "<< arg1<< " and "<< arg2<< ", which is not as expected.")
bool face_orientation(const unsigned int cell, const unsigned int face) const
Definition: tria_objects.h:608
void monitor_memory(const unsigned int true_dimension) const
#define Assert(cond, exc)
Definition: exceptions.h:294
void *& user_pointer(const unsigned int i)
Definition: tria_objects.h:617
std::vector< RefinementCase< G::dimension > > refinement_cases
Definition: tria_objects.h:94
std::vector< BoundaryOrMaterialId > boundary_or_material_id
Definition: tria_objects.h:165
::TriaRawIterator<::TriaAccessor< G::dimension, dim, spacedim > > next_free_single_object(const ::Triangulation< dim, spacedim > &tria)
typename ::Triangulation< dim, spacedim >::raw_hex_iterator next_free_hex(const ::Triangulation< dim, spacedim > &tria, const unsigned int level)
std::vector< types::manifold_id > manifold_id
Definition: tria_objects.h:171
unsigned char boundary_id
Definition: types.h:110
::TriaRawIterator<::TriaAccessor< G::dimension, dim, spacedim > > next_free_pair_object(const ::Triangulation< dim, spacedim > &tria)
void reserve_space(const unsigned int new_objs_in_pairs, const unsigned int new_objs_single=0)
Definition: tria_objects.cc:35
const types::material_id invalid_material_id
Definition: types.h:185