16 #include <deal.II/base/geometry_info.h> 17 #include <deal.II/base/point.h> 18 #include <deal.II/base/tensor.h> 20 #include <deal.II/distributed/shared_tria.h> 21 #include <deal.II/distributed/tria.h> 23 #include <deal.II/dofs/dof_accessor.h> 24 #include <deal.II/dofs/dof_handler.h> 26 #include <deal.II/fe/mapping_q1.h> 27 #include <deal.II/fe/mapping_q_generic.h> 29 #include <deal.II/grid/filtered_iterator.h> 30 #include <deal.II/grid/grid_tools.h> 31 #include <deal.II/grid/tria.h> 32 #include <deal.II/grid/tria_accessor.h> 33 #include <deal.II/grid/tria_iterator.h> 35 #include <deal.II/hp/dof_handler.h> 36 #include <deal.II/hp/mapping_collection.h> 38 #include <deal.II/lac/full_matrix.h> 50 DEAL_II_NAMESPACE_OPEN
54 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
58 const std::vector<bool> & marked_vertices)
66 const std::vector<Point<spacedim>> &vertices = tria.
get_vertices();
69 marked_vertices.size() == 0,
71 marked_vertices.size()));
81 marked_vertices.size() == 0 ||
82 std::equal(marked_vertices.begin(),
83 marked_vertices.end(),
85 [](
bool p,
bool q) {
return !p || q; }),
87 "marked_vertices should be a subset of used vertices in the triangulation " 88 "but marked_vertices contains one or more vertices that are not used vertices!"));
96 const std::vector<bool> &used = (marked_vertices.size() == 0) ?
102 std::vector<bool>::const_iterator first =
103 std::find(used.begin(), used.end(),
true);
109 unsigned int best_vertex = std::distance(used.begin(), first);
110 double best_dist = (p - vertices[best_vertex]).norm_square();
114 for (
unsigned int j = best_vertex + 1; j < vertices.size(); j++)
117 double dist = (p - vertices[j]).norm_square();
118 if (dist < best_dist)
130 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
133 const MeshType<dim, spacedim> &mesh,
135 const std::vector<bool> & marked_vertices)
150 marked_vertices.size() == 0,
152 marked_vertices.size()));
162 marked_vertices.size() == 0 ||
163 std::equal(marked_vertices.begin(),
164 marked_vertices.end(),
166 [](
bool p,
bool q) {
return !p || q; }),
168 "marked_vertices should be a subset of used vertices in the triangulation " 169 "but marked_vertices contains one or more vertices that are not used vertices!"));
172 if (marked_vertices.size())
173 for (
auto it = vertices.begin(); it != vertices.end();)
175 if (marked_vertices[it->first] ==
false)
177 vertices.erase(it++);
190 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
192 std::vector<typename MeshType<dim, spacedim>::active_cell_iterator>
195 typename ::internal::
196 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type>
199 const unsigned int vertex)
204 Assert(vertex < mesh.get_triangulation().n_vertices(),
205 ExcIndexRange(0, mesh.get_triangulation().n_vertices(), vertex));
206 Assert(mesh.get_triangulation().get_used_vertices()[vertex],
212 std::set<typename ::internal::
213 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type>
216 typename ::internal::
217 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type
218 cell = mesh.begin_active(),
254 for (; cell != endc; ++cell)
256 for (
unsigned int v = 0; v < GeometryInfo<dim>::vertices_per_cell; v++)
257 if (cell->vertex_index(v) == vertex)
262 adjacent_cells.insert(cell);
269 for (
unsigned int vface = 0; vface < dim; vface++)
271 const unsigned int face =
274 if (!cell->at_boundary(face) &&
275 cell->neighbor(face)->active())
287 adjacent_cells.insert(cell->neighbor(face));
298 for (
unsigned int e = 0; e < GeometryInfo<dim>::lines_per_cell; ++
e)
299 if (cell->line(e)->has_children())
303 if (cell->line(e)->child(0)->vertex_index(1) == vertex)
305 adjacent_cells.insert(cell);
327 typename ::internal::
328 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type>(
329 adjacent_cells.begin(), adjacent_cells.end());
336 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
338 find_active_cell_around_point_internal(
339 const MeshType<dim, spacedim> &mesh,
341 std::set<
typename MeshType<dim, spacedim>::active_cell_iterator>
343 std::set<
typename MeshType<dim, spacedim>::active_cell_iterator>
347 typename ::internal::
348 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type>
351 typename ::internal::
352 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type>
357 using cell_iterator =
358 typename MeshType<dim, spacedim>::active_cell_iterator;
360 using cell_iterator = typename ::internal::
361 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type;
365 searched_cells.insert(adjacent_cells.begin(), adjacent_cells.end());
369 std::set<cell_iterator> adjacent_cells_new;
371 typename std::set<cell_iterator>::const_iterator cell =
372 adjacent_cells.begin(),
374 adjacent_cells.end();
375 for (; cell != endc; ++cell)
377 std::vector<cell_iterator> active_neighbors;
378 get_active_neighbors<MeshType<dim, spacedim>>(*cell,
380 for (
unsigned int i = 0; i < active_neighbors.size(); ++i)
381 if (searched_cells.find(active_neighbors[i]) ==
382 searched_cells.end())
383 adjacent_cells_new.insert(active_neighbors[i]);
385 adjacent_cells.clear();
386 adjacent_cells.insert(adjacent_cells_new.begin(),
387 adjacent_cells_new.end());
388 if (adjacent_cells.size() == 0)
396 cell_iterator it = mesh.begin_active();
397 for (; it != mesh.end(); ++it)
398 if (searched_cells.find(it) == searched_cells.end())
400 adjacent_cells.insert(it);
408 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
410 std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
414 typename ::internal::
415 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type,
418 find_active_cell_around_point_tolerance(
420 const MeshType<dim, spacedim> &mesh,
422 const std::vector<bool> & marked_vertices,
423 const double tolerance)
425 using active_cell_iterator = typename ::internal::
426 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type;
432 double best_distance = tolerance;
434 std::pair<active_cell_iterator, Point<dim>> best_cell;
438 std::vector<active_cell_iterator> adjacent_cells_tmp =
447 std::set<active_cell_iterator> adjacent_cells(adjacent_cells_tmp.begin(),
448 adjacent_cells_tmp.end());
449 std::set<active_cell_iterator> searched_cells;
457 const unsigned int n_active_cells =
458 mesh.get_triangulation().n_active_cells();
460 unsigned int cells_searched = 0;
461 while (!found && cells_searched < n_active_cells)
463 typename std::set<active_cell_iterator>::const_iterator
464 cell = adjacent_cells.begin(),
465 endc = adjacent_cells.end();
466 for (; cell != endc; ++cell)
482 if ((dist < best_distance) ||
483 ((dist == best_distance) &&
484 ((*cell)->level() > best_level)))
487 best_distance = dist;
488 best_level = (*cell)->level();
489 best_cell = std::make_pair(*cell, p_cell);
511 cells_searched += adjacent_cells.size();
516 if (marked_vertices.size() > 0)
517 cells_searched = n_active_cells;
526 if (!found && cells_searched < n_active_cells)
528 find_active_cell_around_point_internal<dim, MeshType, spacedim>(
529 mesh, searched_cells, adjacent_cells);
534 ExcPointNotFound<spacedim>(p));
542 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
544 typename MeshType<dim, spacedim>::active_cell_iterator
546 typename ::internal::
547 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type
551 const std::vector<bool> & marked_vertices)
553 return find_active_cell_around_point<dim, MeshType, spacedim>(
560 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
562 std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
Point<dim>>
564 std::pair<typename ::internal::
565 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type,
569 const MeshType<dim, spacedim> &mesh,
571 const std::vector<bool> & marked_vertices)
573 return find_active_cell_around_point_tolerance(
574 mapping, mesh, p, marked_vertices, 1e-10);
579 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
581 std::vector<std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
584 std::vector<std::pair<
585 typename ::internal::
586 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type,
590 const MeshType<dim, spacedim> &mesh,
592 const double tolerance,
593 const std::vector<bool> &marked_vertices)
601 std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
606 cells_and_points.push_back(find_active_cell_around_point_tolerance(
607 mapping, mesh, p, marked_vertices, tolerance));
609 catch (ExcPointNotFound<spacedim> &)
612 if (!cells_and_points.empty())
616 const Point<dim> unit_point = cells_and_points.front().second;
617 const auto my_cell = cells_and_points.front().first;
619 unsigned int n_dirs_at_threshold = 0;
621 for (
unsigned int d = 0; d < dim; ++d)
623 distance_to_center[d] = std::abs(unit_point[d] - 0.5);
624 if (distance_to_center[d] > 0.5 - tolerance)
626 ++n_dirs_at_threshold;
627 last_point_at_threshold = d;
631 std::vector<typename MeshType<dim, spacedim>::active_cell_iterator>
634 if (n_dirs_at_threshold == 1)
636 unsigned int neighbor_index =
637 2 * last_point_at_threshold +
638 (unit_point[last_point_at_threshold] > 0.5 ? 1 : 0);
639 if (!my_cell->at_boundary(neighbor_index))
640 cells_to_add.push_back(my_cell->neighbor(neighbor_index));
643 else if (n_dirs_at_threshold == dim)
645 unsigned int local_vertex_index = 0;
646 for (
unsigned int d = 0; d < dim; ++d)
647 local_vertex_index += (unit_point[d] > 0.5 ? 1 : 0) << d;
648 std::vector<typename MeshType<dim, spacedim>::active_cell_iterator>
650 mesh, my_cell->vertex_index(local_vertex_index));
651 for (
const auto &cell : cells)
653 cells_to_add.push_back(cell);
660 else if (n_dirs_at_threshold == 2)
662 std::pair<unsigned int, unsigned int> vertex_indices[3];
663 unsigned int count_vertex_indices = 0;
665 for (
unsigned int d = 0; d < dim; ++d)
667 if (distance_to_center[d] > 0.5 - tolerance)
669 vertex_indices[count_vertex_indices].first = d;
670 vertex_indices[count_vertex_indices].second =
671 unit_point[d] > 0.5 ? 1 : 0;
672 count_vertex_indices++;
682 const unsigned int first_vertex =
683 (vertex_indices[0].second << vertex_indices[0].first) +
684 (vertex_indices[1].second << vertex_indices[1].first);
685 for (
unsigned int d = 0; d < 2; ++d)
689 my_cell->vertex_index(first_vertex + (d << free_direction)));
690 for (
const auto &cell : tentative_cells)
692 bool cell_not_yet_present =
true;
693 for (
const auto &other_cell : cells_to_add)
694 if (cell == other_cell)
696 cell_not_yet_present =
false;
699 if (cell_not_yet_present)
700 cells_to_add.push_back(cell);
705 const double original_distance_to_unit_cell =
707 for (
auto cell : cells_to_add)
715 original_distance_to_unit_cell + tolerance)
716 cells_and_points.emplace_back(cell, p_unit);
723 cells_and_points.begin(),
724 cells_and_points.end(),
725 [](
const std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
727 const std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
728 Point<dim>> &b) {
return a.first < b.first; });
730 return cells_and_points;
735 template <
class MeshType>
736 std::vector<typename MeshType::active_cell_iterator>
738 const MeshType &mesh,
739 const std::function<
bool(
const typename MeshType::active_cell_iterator &)>
742 std::vector<typename MeshType::active_cell_iterator> active_halo_layer;
743 std::vector<bool> locally_active_vertices_on_subdomain(
744 mesh.get_triangulation().n_vertices(),
false);
749 for (
typename MeshType::active_cell_iterator cell = mesh.begin_active();
753 for (
unsigned int v = 0;
754 v < GeometryInfo<MeshType::dimension>::vertices_per_cell;
756 locally_active_vertices_on_subdomain[cell->vertex_index(v)] =
true;
761 for (
typename MeshType::active_cell_iterator cell = mesh.begin_active();
764 if (!predicate(cell))
765 for (
unsigned int v = 0;
766 v < GeometryInfo<MeshType::dimension>::vertices_per_cell;
768 if (locally_active_vertices_on_subdomain[cell->vertex_index(v)] ==
771 active_halo_layer.push_back(cell);
775 return active_halo_layer;
780 template <
class MeshType>
781 std::vector<typename MeshType::cell_iterator>
783 const MeshType &mesh,
784 const std::function<
bool(
const typename MeshType::cell_iterator &)>
786 const unsigned int level)
788 std::vector<typename MeshType::cell_iterator> level_halo_layer;
789 std::vector<bool> locally_active_vertices_on_level_subdomain(
790 mesh.get_triangulation().n_vertices(),
false);
795 for (
typename MeshType::cell_iterator cell = mesh.begin(level);
796 cell != mesh.end(level);
799 for (
unsigned int v = 0;
800 v < GeometryInfo<MeshType::dimension>::vertices_per_cell;
802 locally_active_vertices_on_level_subdomain[cell->vertex_index(v)] =
808 for (
typename MeshType::cell_iterator cell = mesh.begin(level);
809 cell != mesh.end(level);
811 if (!predicate(cell))
812 for (
unsigned int v = 0;
813 v < GeometryInfo<MeshType::dimension>::vertices_per_cell;
815 if (locally_active_vertices_on_level_subdomain[cell->vertex_index(
818 level_halo_layer.push_back(cell);
822 return level_halo_layer;
828 template <
class MeshType>
830 contains_locally_owned_cells(
831 const std::vector<typename MeshType::active_cell_iterator> &cells)
833 for (
typename std::vector<
834 typename MeshType::active_cell_iterator>::const_iterator it =
839 if ((*it)->is_locally_owned())
845 template <
class MeshType>
847 contains_artificial_cells(
848 const std::vector<typename MeshType::active_cell_iterator> &cells)
850 for (
typename std::vector<
851 typename MeshType::active_cell_iterator>::const_iterator it =
856 if ((*it)->is_artificial())
865 template <
class MeshType>
866 std::vector<typename MeshType::active_cell_iterator>
869 std::function<bool(const typename MeshType::active_cell_iterator &)>
872 const std::vector<typename MeshType::active_cell_iterator>
877 Assert(contains_locally_owned_cells<MeshType>(active_halo_layer) ==
false,
878 ExcMessage(
"Halo layer contains locally owned cells"));
879 Assert(contains_artificial_cells<MeshType>(active_halo_layer) ==
false,
880 ExcMessage(
"Halo layer contains artificial cells"));
882 return active_halo_layer;
887 template <
class MeshType>
888 std::vector<typename MeshType::active_cell_iterator>
890 const MeshType &mesh,
891 const std::function<
bool(
const typename MeshType::active_cell_iterator &)>
893 const double layer_thickness)
895 std::vector<typename MeshType::active_cell_iterator>
896 subdomain_boundary_cells, active_cell_layer_within_distance;
897 std::vector<bool> vertices_outside_subdomain(
898 mesh.get_triangulation().n_vertices(),
false);
900 const unsigned int spacedim = MeshType::space_dimension;
902 unsigned int n_non_predicate_cells = 0;
910 for (
typename MeshType::active_cell_iterator cell = mesh.begin_active();
913 if (!predicate(cell))
915 for (
unsigned int v = 0;
916 v < GeometryInfo<MeshType::dimension>::vertices_per_cell;
918 vertices_outside_subdomain[cell->vertex_index(v)] =
true;
919 n_non_predicate_cells++;
926 if (n_non_predicate_cells == 0 ||
927 n_non_predicate_cells == mesh.get_triangulation().n_active_cells())
928 return std::vector<typename MeshType::active_cell_iterator>();
932 for (
typename MeshType::active_cell_iterator cell = mesh.begin_active();
937 for (
unsigned int v = 0;
938 v < GeometryInfo<MeshType::dimension>::vertices_per_cell;
940 if (vertices_outside_subdomain[cell->vertex_index(v)] ==
true)
942 subdomain_boundary_cells.push_back(cell);
952 const double &DOUBLE_EPSILON =
953 100. * std::numeric_limits<double>::epsilon();
956 for (
unsigned int d = 0; d < spacedim; ++d)
958 bounding_box.first[d] -= (layer_thickness + DOUBLE_EPSILON);
959 bounding_box.second[d] += (layer_thickness + DOUBLE_EPSILON);
962 std::vector<Point<spacedim>>
963 subdomain_boundary_cells_centers;
966 subdomain_boundary_cells_radii;
968 subdomain_boundary_cells_centers.reserve(subdomain_boundary_cells.size());
969 subdomain_boundary_cells_radii.reserve(subdomain_boundary_cells.size());
971 for (
typename std::vector<typename MeshType::active_cell_iterator>::
972 const_iterator subdomain_boundary_cell_iterator =
973 subdomain_boundary_cells.begin();
974 subdomain_boundary_cell_iterator != subdomain_boundary_cells.end();
975 ++subdomain_boundary_cell_iterator)
977 const std::pair<Point<spacedim>,
double>
978 &subdomain_boundary_cell_enclosing_ball =
979 (*subdomain_boundary_cell_iterator)->enclosing_ball();
981 subdomain_boundary_cells_centers.push_back(
982 subdomain_boundary_cell_enclosing_ball.first);
983 subdomain_boundary_cells_radii.push_back(
984 subdomain_boundary_cell_enclosing_ball.second);
986 AssertThrow(subdomain_boundary_cells_radii.size() ==
987 subdomain_boundary_cells_centers.size(),
996 for (
typename MeshType::active_cell_iterator cell = mesh.begin_active();
1001 if (predicate(cell))
1004 const std::pair<Point<spacedim>,
double> &cell_enclosing_ball =
1005 cell->enclosing_ball();
1008 cell_enclosing_ball.first;
1009 const double &cell_enclosing_ball_radius = cell_enclosing_ball.second;
1011 bool cell_inside =
true;
1013 for (
unsigned int d = 0; d < spacedim; ++d)
1015 (cell_enclosing_ball_center[d] + cell_enclosing_ball_radius >
1016 bounding_box.first[d]) &&
1017 (cell_enclosing_ball_center[d] - cell_enclosing_ball_radius <
1018 bounding_box.second[d]);
1024 for (
unsigned int i = 0; i < subdomain_boundary_cells_radii.size();
1027 subdomain_boundary_cells_centers[i]) <
1028 Utilities::fixed_power<2>(cell_enclosing_ball_radius +
1029 subdomain_boundary_cells_radii[i] +
1030 layer_thickness + DOUBLE_EPSILON))
1032 active_cell_layer_within_distance.push_back(cell);
1037 return active_cell_layer_within_distance;
1042 template <
class MeshType>
1043 std::vector<typename MeshType::active_cell_iterator>
1045 const double layer_thickness)
1048 std::function<bool(const typename MeshType::active_cell_iterator &)>
1049 predicate(locally_owned_cell_predicate);
1051 const std::vector<typename MeshType::active_cell_iterator>
1052 ghost_cell_layer_within_distance =
1060 contains_locally_owned_cells<MeshType>(
1061 ghost_cell_layer_within_distance) ==
false,
1063 "Ghost cells within layer_thickness contains locally owned cells."));
1065 contains_artificial_cells<MeshType>(ghost_cell_layer_within_distance) ==
1068 "Ghost cells within layer_thickness contains artificial cells." 1069 "The function compute_ghost_cell_layer_within_distance " 1070 "is probably called while using parallel::distributed::Triangulation. " 1071 "In such case please refer to the description of this function."));
1073 return ghost_cell_layer_within_distance;
1078 template <
class MeshType>
1081 const MeshType &mesh,
1082 const std::function<
bool(
const typename MeshType::active_cell_iterator &)>
1085 std::vector<bool> locally_active_vertices_on_subdomain(
1086 mesh.get_triangulation().n_vertices(),
false);
1088 const unsigned int spacedim = MeshType::space_dimension;
1095 for (
typename MeshType::active_cell_iterator cell = mesh.begin_active();
1098 if (predicate(cell))
1100 minp = cell->center();
1101 maxp = cell->center();
1107 for (
typename MeshType::active_cell_iterator cell = mesh.begin_active();
1110 if (predicate(cell))
1111 for (
unsigned int v = 0;
1112 v < GeometryInfo<MeshType::dimension>::vertices_per_cell;
1114 if (locally_active_vertices_on_subdomain[cell->vertex_index(v)] ==
1117 locally_active_vertices_on_subdomain[cell->vertex_index(v)] =
1119 for (
unsigned int d = 0; d < spacedim; ++d)
1121 minp[d] = std::min(minp[d], cell->vertex(v)[d]);
1122 maxp[d] = std::max(maxp[d], cell->vertex(v)[d]);
1126 return std::make_pair(minp, maxp);
1131 template <
typename MeshType>
1132 std::list<std::pair<
typename MeshType::cell_iterator,
1133 typename MeshType::cell_iterator>>
1137 ExcMessage(
"The two meshes must be represent triangulations that " 1138 "have the same coarse meshes"));
1155 using CellList = std::list<std::pair<
typename MeshType::cell_iterator,
1156 typename MeshType::cell_iterator>>;
1160 typename MeshType::cell_iterator cell_1 = mesh_1.begin(0),
1161 cell_2 = mesh_2.begin(0);
1162 for (; cell_1 != mesh_1.end(0); ++cell_1, ++cell_2)
1163 cell_list.emplace_back(cell_1, cell_2);
1167 typename CellList::iterator cell_pair = cell_list.begin();
1168 while (cell_pair != cell_list.end())
1174 if (cell_pair->first->has_children() &&
1175 cell_pair->second->has_children())
1177 Assert(cell_pair->first->refinement_case() ==
1178 cell_pair->second->refinement_case(),
1180 for (
unsigned int c = 0; c < cell_pair->first->n_children(); ++c)
1181 cell_list.emplace_back(cell_pair->first->child(c),
1182 cell_pair->second->child(c));
1191 const typename CellList::iterator previous_cell_pair = cell_pair;
1194 cell_list.erase(previous_cell_pair);
1206 for (cell_pair = cell_list.begin(); cell_pair != cell_list.end();
1208 Assert(cell_pair->first->active() || cell_pair->second->active() ||
1209 (cell_pair->first->refinement_case() !=
1210 cell_pair->second->refinement_case()),
1218 template <
int dim,
int spacedim>
1235 endc = mesh_1.
end(0);
1236 for (; cell_1 != endc; ++cell_1, ++cell_2)
1237 for (
unsigned int v = 0; v < GeometryInfo<dim>::vertices_per_cell; ++v)
1238 if (cell_1->vertex(v) != cell_2->vertex(v))
1250 template <
typename MeshType>
1255 mesh_2.get_triangulation());
1260 template <
int dim,
int spacedim>
1261 std::pair<typename hp::DoFHandler<dim, spacedim>::active_cell_iterator,
1270 ExcMessage(
"Mapping collection needs to have either size 1 " 1271 "or size equal to the number of elements in " 1272 "the FECollection."));
1274 using cell_iterator =
1277 std::pair<cell_iterator, Point<dim>> best_cell;
1281 if (mapping.
size() == 1)
1289 double best_distance = 1e-10;
1290 int best_level = -1;
1297 std::vector<cell_iterator> adjacent_cells_tmp =
1305 std::set<cell_iterator> adjacent_cells(adjacent_cells_tmp.begin(),
1306 adjacent_cells_tmp.end());
1307 std::set<cell_iterator> searched_cells;
1317 unsigned int cells_searched = 0;
1318 while (!found && cells_searched < n_cells)
1320 typename std::set<cell_iterator>::const_iterator
1321 cell = adjacent_cells.begin(),
1322 endc = adjacent_cells.end();
1323 for (; cell != endc; ++cell)
1328 mapping[(*cell)->active_fe_index()]
1329 .transform_real_to_unit_cell(*cell, p);
1341 if (dist < best_distance || (dist == best_distance &&
1342 (*cell)->level() > best_level))
1345 best_distance = dist;
1346 best_level = (*cell)->level();
1347 best_cell = std::make_pair(*cell, p_cell);
1352 spacedim>::ExcTransformationFailed &)
1368 cells_searched += adjacent_cells.size();
1374 if (!found && cells_searched < n_cells)
1376 find_active_cell_around_point_internal<dim,
1379 mesh, searched_cells, adjacent_cells);
1385 ExcPointNotFound<spacedim>(p));
1391 template <
class MeshType>
1392 std::vector<typename MeshType::active_cell_iterator>
1395 Assert(cell->is_locally_owned(),
1396 ExcMessage(
"This function only makes sense if the cell for " 1397 "which you are asking for a patch, is locally " 1400 std::vector<typename MeshType::active_cell_iterator> patch;
1401 patch.push_back(cell);
1402 for (
unsigned int face_number = 0;
1403 face_number < GeometryInfo<MeshType::dimension>::faces_per_cell;
1405 if (cell->face(face_number)->at_boundary() ==
false)
1407 if (cell->neighbor(face_number)->has_children() ==
false)
1408 patch.push_back(cell->neighbor(face_number));
1413 if (MeshType::dimension > 1)
1415 for (
unsigned int subface = 0;
1416 subface < cell->face(face_number)->n_children();
1419 cell->neighbor_child_on_subface(face_number, subface));
1425 typename MeshType::cell_iterator neighbor =
1426 cell->neighbor(face_number);
1427 while (neighbor->has_children())
1428 neighbor = neighbor->child(1 - face_number);
1430 Assert(neighbor->neighbor(1 - face_number) == cell,
1432 patch.push_back(neighbor);
1440 template <
class Container>
1441 std::vector<typename Container::cell_iterator>
1443 const std::vector<typename Container::active_cell_iterator> &patch)
1447 "Vector containing patch cells should not be an empty vector!"));
1451 int min_level = patch[0]->level();
1453 for (
unsigned int i = 0; i < patch.size(); ++i)
1454 min_level = std::min(min_level, patch[i]->level());
1455 std::set<typename Container::cell_iterator> uniform_cells;
1456 typename std::vector<
1457 typename Container::active_cell_iterator>::const_iterator patch_cell;
1459 for (patch_cell = patch.begin(); patch_cell != patch.end(); ++patch_cell)
1464 if ((*patch_cell)->level() == min_level)
1465 uniform_cells.insert(*patch_cell);
1472 typename Container::cell_iterator parent = *patch_cell;
1474 while (parent->level() > min_level)
1475 parent = parent->parent();
1476 uniform_cells.insert(parent);
1480 return std::vector<typename Container::cell_iterator>(uniform_cells.begin(),
1481 uniform_cells.end());
1486 template <
class Container>
1489 const std::vector<typename Container::active_cell_iterator> &patch,
1491 &local_triangulation,
1494 Container::space_dimension>::active_cell_iterator,
1495 typename Container::active_cell_iterator> &patch_to_global_tria_map)
1498 const std::vector<typename Container::cell_iterator> uniform_cells =
1499 get_cells_at_coarsest_common_level<Container>(patch);
1501 local_triangulation.
clear();
1502 std::vector<Point<Container::space_dimension>> vertices;
1503 const unsigned int n_uniform_cells = uniform_cells.size();
1504 std::vector<CellData<Container::dimension>> cells(n_uniform_cells);
1507 typename std::vector<typename Container::cell_iterator>::const_iterator
1509 for (uniform_cell = uniform_cells.begin();
1510 uniform_cell != uniform_cells.end();
1513 for (
unsigned int v = 0;
1514 v < GeometryInfo<Container::dimension>::vertices_per_cell;
1518 (*uniform_cell)->vertex(v);
1519 bool repeat_vertex =
false;
1521 for (
unsigned int m = 0; m < i; ++m)
1523 if (position == vertices[m])
1525 repeat_vertex =
true;
1526 cells[k].vertices[v] = m;
1530 if (repeat_vertex ==
false)
1532 vertices.push_back(position);
1533 cells[k].vertices[v] = i;
1544 unsigned int index = 0;
1547 Container::space_dimension>::cell_iterator,
1548 typename Container::cell_iterator>
1549 patch_to_global_tria_map_tmp;
1551 Container::space_dimension>::cell_iterator
1552 coarse_cell = local_triangulation.
begin();
1553 coarse_cell != local_triangulation.
end();
1554 ++coarse_cell, ++index)
1556 patch_to_global_tria_map_tmp.insert(
1557 std::make_pair(coarse_cell, uniform_cells[index]));
1561 Assert(coarse_cell->center().distance(uniform_cells[index]->center()) <=
1562 1e-15 * coarse_cell->diameter(),
1565 bool refinement_necessary;
1570 refinement_necessary =
false;
1572 Container::space_dimension>::
1573 active_cell_iterator active_tria_cell =
1575 active_tria_cell != local_triangulation.
end();
1578 if (patch_to_global_tria_map_tmp[active_tria_cell]->has_children())
1580 active_tria_cell->set_refine_flag();
1581 refinement_necessary =
true;
1584 for (
unsigned int i = 0; i < patch.size(); ++i)
1589 if (patch_to_global_tria_map_tmp[active_tria_cell] ==
1594 for (
unsigned int v = 0;
1596 Container::dimension>::vertices_per_cell;
1598 active_tria_cell->vertex(v) = patch[i]->vertex(v);
1600 Assert(active_tria_cell->center().distance(
1601 patch_to_global_tria_map_tmp[active_tria_cell]
1603 1e-15 * active_tria_cell->diameter(),
1606 active_tria_cell->set_user_flag();
1612 if (refinement_necessary)
1617 Container::dimension,
1618 Container::space_dimension>::cell_iterator cell =
1619 local_triangulation.
begin();
1620 cell != local_triangulation.
end();
1623 if (patch_to_global_tria_map_tmp.find(cell) !=
1624 patch_to_global_tria_map_tmp.end())
1626 if (cell->has_children())
1633 for (
unsigned int c = 0; c < cell->n_children(); ++c)
1635 if (patch_to_global_tria_map_tmp.find(cell->child(
1636 c)) == patch_to_global_tria_map_tmp.end())
1638 patch_to_global_tria_map_tmp.insert(
1641 patch_to_global_tria_map_tmp[cell]->child(
1663 patch_to_global_tria_map_tmp.erase(cell);
1669 while (refinement_necessary);
1675 Container::space_dimension>::cell_iterator
1676 cell = local_triangulation.
begin();
1677 cell != local_triangulation.
end();
1680 if (cell->user_flag_set())
1682 Assert(patch_to_global_tria_map_tmp.find(cell) !=
1683 patch_to_global_tria_map_tmp.end(),
1686 Assert(cell->center().distance(
1687 patch_to_global_tria_map_tmp[cell]->center()) <=
1688 1e-15 * cell->diameter(),
1696 Container::space_dimension>::cell_iterator,
1697 typename Container::cell_iterator>::iterator
1698 map_tmp_it = patch_to_global_tria_map_tmp.
begin(),
1699 map_tmp_end = patch_to_global_tria_map_tmp.end();
1703 for (; map_tmp_it != map_tmp_end; ++map_tmp_it)
1704 patch_to_global_tria_map[map_tmp_it->first] = map_tmp_it->second;
1709 template <
class DoFHandlerType>
1711 std::vector<typename DoFHandlerType::active_cell_iterator>>
1725 std::set<typename DoFHandlerType::active_cell_iterator>>
1726 dof_to_set_of_cells_map;
1728 std::vector<types::global_dof_index> local_dof_indices;
1729 std::vector<types::global_dof_index> local_face_dof_indices;
1730 std::vector<types::global_dof_index> local_line_dof_indices;
1734 std::vector<bool> user_flags;
1739 std::map<
typename DoFHandlerType::active_line_iterator,
1740 typename DoFHandlerType::line_iterator>
1741 lines_to_parent_lines_map;
1742 if (DoFHandlerType::dimension == 3)
1745 dof_handler.get_triangulation().save_user_flags(user_flags);
1747 DoFHandlerType::space_dimension
> &>(
1748 dof_handler.get_triangulation())
1749 .clear_user_flags();
1752 typename DoFHandlerType::active_cell_iterator cell = dof_handler
1754 endc = dof_handler.end();
1755 for (; cell != endc; ++cell)
1761 if (cell->is_artificial() ==
false)
1763 for (
unsigned int l = 0;
1767 if (cell->line(l)->has_children())
1768 for (
unsigned int c = 0; c < cell->line(l)->n_children();
1771 lines_to_parent_lines_map[cell->line(l)->child(c)] =
1775 cell->line(l)->child(c)->set_user_flag();
1788 typename DoFHandlerType::active_cell_iterator cell =
1789 dof_handler.begin_active(),
1790 endc = dof_handler.end();
1791 for (; cell != endc; ++cell)
1796 if (cell->is_artificial() ==
false)
1798 const unsigned int n_dofs_per_cell = cell->get_fe().dofs_per_cell;
1799 local_dof_indices.resize(n_dofs_per_cell);
1803 cell->get_dof_indices(local_dof_indices);
1804 for (
unsigned int i = 0; i < n_dofs_per_cell; ++i)
1805 dof_to_set_of_cells_map[local_dof_indices[i]].insert(cell);
1815 for (
unsigned int f = 0;
1816 f < GeometryInfo<DoFHandlerType::dimension>::faces_per_cell;
1819 if (cell->face(f)->has_children())
1821 for (
unsigned int c = 0; c < cell->face(f)->n_children();
1836 Assert(cell->face(f)->child(c)->has_children() ==
false,
1839 const unsigned int n_dofs_per_face =
1840 cell->get_fe().dofs_per_face;
1841 local_face_dof_indices.resize(n_dofs_per_face);
1843 cell->face(f)->child(c)->get_dof_indices(
1844 local_face_dof_indices);
1845 for (
unsigned int i = 0; i < n_dofs_per_face; ++i)
1846 dof_to_set_of_cells_map[local_face_dof_indices[i]]
1850 else if ((cell->face(f)->at_boundary() ==
false) &&
1851 (cell->neighbor_is_coarser(f)))
1868 std::pair<unsigned int, unsigned int>
1869 neighbor_face_no_subface_no =
1870 cell->neighbor_of_coarser_neighbor(f);
1871 unsigned int face_no = neighbor_face_no_subface_no.first;
1872 unsigned int subface = neighbor_face_no_subface_no.second;
1874 const unsigned int n_dofs_per_face =
1875 cell->get_fe().dofs_per_face;
1876 local_face_dof_indices.resize(n_dofs_per_face);
1878 cell->neighbor(f)->face(face_no)->get_dof_indices(
1879 local_face_dof_indices);
1880 for (
unsigned int i = 0; i < n_dofs_per_face; ++i)
1881 dof_to_set_of_cells_map[local_face_dof_indices[i]].insert(
1886 for (
unsigned int c = 0;
1887 c < cell->neighbor(f)->face(face_no)->n_children();
1893 const unsigned int n_dofs_per_face =
1894 cell->get_fe().dofs_per_face;
1895 local_face_dof_indices.resize(n_dofs_per_face);
1900 ->has_children() ==
false,
1905 ->get_dof_indices(local_face_dof_indices);
1906 for (
unsigned int i = 0; i < n_dofs_per_face; ++i)
1907 dof_to_set_of_cells_map[local_face_dof_indices[i]]
1922 if (DoFHandlerType::dimension == 3)
1924 for (
unsigned int l = 0;
1929 if (cell->line(l)->has_children())
1931 for (
unsigned int c = 0;
1932 c < cell->line(l)->n_children();
1935 Assert(cell->line(l)->child(c)->has_children() ==
1941 const unsigned int n_dofs_per_line =
1942 2 * cell->get_fe().dofs_per_vertex +
1943 cell->get_fe().dofs_per_line;
1944 local_line_dof_indices.resize(n_dofs_per_line);
1946 cell->line(l)->child(c)->get_dof_indices(
1947 local_line_dof_indices);
1948 for (
unsigned int i = 0; i < n_dofs_per_line; ++i)
1949 dof_to_set_of_cells_map[local_line_dof_indices[i]]
1957 else if (cell->line(l)->user_flag_set() ==
true)
1959 typename DoFHandlerType::line_iterator parent_line =
1960 lines_to_parent_lines_map[cell->line(l)];
1965 const unsigned int n_dofs_per_line =
1966 2 * cell->get_fe().dofs_per_vertex +
1967 cell->get_fe().dofs_per_line;
1968 local_line_dof_indices.resize(n_dofs_per_line);
1970 parent_line->get_dof_indices(local_line_dof_indices);
1971 for (
unsigned int i = 0; i < n_dofs_per_line; ++i)
1972 dof_to_set_of_cells_map[local_line_dof_indices[i]]
1975 for (
unsigned int c = 0; c < parent_line->n_children();
1978 Assert(parent_line->child(c)->has_children() ==
1982 const unsigned int n_dofs_per_line =
1983 2 * cell->get_fe().dofs_per_vertex +
1984 cell->get_fe().dofs_per_line;
1985 local_line_dof_indices.resize(n_dofs_per_line);
1987 parent_line->child(c)->get_dof_indices(
1988 local_line_dof_indices);
1989 for (
unsigned int i = 0; i < n_dofs_per_line; ++i)
1990 dof_to_set_of_cells_map[local_line_dof_indices[i]]
2000 if (DoFHandlerType::dimension == 3)
2006 DoFHandlerType::space_dimension
> &>(
2007 dof_handler.get_triangulation())
2008 .load_user_flags(user_flags);
2014 std::vector<typename DoFHandlerType::active_cell_iterator>>
2015 dof_to_cell_patches;
2018 std::set<typename DoFHandlerType::active_cell_iterator>>::
2019 iterator it = dof_to_set_of_cells_map.begin(),
2020 it_end = dof_to_set_of_cells_map.end();
2021 for (; it != it_end; ++it)
2022 dof_to_cell_patches[it->first].assign(it->second.begin(),
2025 return dof_to_cell_patches;
2031 template <
typename CellIterator>
2033 match_periodic_face_pairs(
2034 std::set<std::pair<CellIterator, unsigned int>> &pairs1,
2035 std::set<std::pair<
typename identity<CellIterator>::type,
unsigned int>>
2037 const int direction,
2039 const ::Tensor<1, CellIterator::AccessorType::space_dimension>
2043 static const int space_dim = CellIterator::AccessorType::space_dimension;
2045 Assert(0 <= direction && direction < space_dim,
2048 Assert(pairs1.size() == pairs2.size(),
2049 ExcMessage(
"Unmatched faces on periodic boundaries"));
2051 unsigned int n_matches = 0;
2054 std::bitset<3> orientation;
2055 using PairIterator =
2056 typename std::set<std::pair<CellIterator, unsigned int>>::const_iterator;
2057 for (PairIterator it1 = pairs1.begin(); it1 != pairs1.end(); ++it1)
2059 for (PairIterator it2 = pairs2.begin(); it2 != pairs2.end(); ++it2)
2061 const CellIterator cell1 = it1->first;
2062 const CellIterator cell2 = it2->first;
2063 const unsigned int face_idx1 = it1->second;
2064 const unsigned int face_idx2 = it2->second;
2066 cell1->face(face_idx1),
2067 cell2->face(face_idx2),
2076 {cell1, cell2}, {face_idx1, face_idx2}, orientation, matrix};
2077 matched_pairs.push_back(matched_face);
2086 AssertThrow(n_matches == pairs1.size() && pairs2.size() == 0,
2087 ExcMessage(
"Unmatched faces on periodic boundaries"));
2092 template <
typename MeshType>
2095 const MeshType & mesh,
2097 const int direction,
2103 static const int dim = MeshType::dimension;
2104 static const int space_dim = MeshType::space_dimension;
2107 Assert(0 <= direction && direction < space_dim,
2115 std::set<std::pair<typename MeshType::cell_iterator, unsigned int>> pairs1;
2116 std::set<std::pair<typename MeshType::cell_iterator, unsigned int>> pairs2;
2118 for (
typename MeshType::cell_iterator cell = mesh.begin(0);
2119 cell != mesh.end(0);
2122 const typename MeshType::face_iterator face_1 =
2123 cell->face(2 * direction);
2124 const typename MeshType::face_iterator face_2 =
2125 cell->face(2 * direction + 1);
2127 if (face_1->at_boundary() && face_1->boundary_id() == b_id)
2129 const std::pair<typename MeshType::cell_iterator, unsigned int>
2130 pair1 = std::make_pair(cell, 2 * direction);
2131 pairs1.insert(pair1);
2134 if (face_2->at_boundary() && face_2->boundary_id() == b_id)
2136 const std::pair<typename MeshType::cell_iterator, unsigned int>
2137 pair2 = std::make_pair(cell, 2 * direction + 1);
2138 pairs2.insert(pair2);
2142 Assert(pairs1.size() == pairs2.size(),
2143 ExcMessage(
"Unmatched faces on periodic boundaries"));
2145 Assert(pairs1.size() > 0,
2146 ExcMessage(
"No new periodic face pairs have been found. " 2147 "Are you sure that you've selected the correct boundary " 2148 "id's and that the coarsest level mesh is colorized?"));
2151 const unsigned int size_old = matched_pairs.size();
2155 match_periodic_face_pairs(
2156 pairs1, pairs2, direction, matched_pairs, offset, matrix);
2160 const unsigned int size_new = matched_pairs.size();
2161 for (
unsigned int i = size_old; i < size_new; ++i)
2163 Assert(matched_pairs[i].orientation == 1,
2165 "Found a face match with non standard orientation. " 2166 "This function is only suitable for meshes with cells " 2167 "in default orientation"));
2174 template <
typename MeshType>
2177 const MeshType & mesh,
2180 const int direction,
2186 static const int dim = MeshType::dimension;
2187 static const int space_dim = MeshType::space_dimension;
2190 Assert(0 <= direction && direction < space_dim,
2196 std::set<std::pair<typename MeshType::cell_iterator, unsigned int>> pairs1;
2197 std::set<std::pair<typename MeshType::cell_iterator, unsigned int>> pairs2;
2199 for (
typename MeshType::cell_iterator cell = mesh.begin(0);
2200 cell != mesh.end(0);
2203 for (
unsigned int i = 0; i < GeometryInfo<dim>::faces_per_cell; ++i)
2205 const typename MeshType::face_iterator face = cell->face(i);
2206 if (face->at_boundary() && face->boundary_id() == b_id1)
2208 const std::pair<typename MeshType::cell_iterator, unsigned int>
2209 pair1 = std::make_pair(cell, i);
2210 pairs1.insert(pair1);
2213 if (face->at_boundary() && face->boundary_id() == b_id2)
2215 const std::pair<typename MeshType::cell_iterator, unsigned int>
2216 pair2 = std::make_pair(cell, i);
2217 pairs2.insert(pair2);
2222 Assert(pairs1.size() == pairs2.size(),
2223 ExcMessage(
"Unmatched faces on periodic boundaries"));
2225 Assert(pairs1.size() > 0,
2226 ExcMessage(
"No new periodic face pairs have been found. " 2227 "Are you sure that you've selected the correct boundary " 2228 "id's and that the coarsest level mesh is colorized?"));
2231 match_periodic_face_pairs(
2232 pairs1, pairs2, direction, matched_pairs, offset, matrix);
2246 template <
int spacedim>
2250 const int direction,
2254 Assert(0 <= direction && direction < spacedim,
2261 if (matrix.
m() == spacedim)
2262 for (
int i = 0; i < spacedim; ++i)
2263 for (
int j = 0; j < spacedim; ++j)
2264 distance(i) += matrix(i, j) * point1(j);
2268 distance += offset - point2;
2270 for (
int i = 0; i < spacedim; ++i)
2276 if (fabs(distance(i)) > 1.e-10)
2295 struct OrientationLookupTable
2299 struct OrientationLookupTable<1>
2302 std::array<unsigned int, GeometryInfo<1>::vertices_per_face>;
2303 static inline std::bitset<3>
2304 lookup(
const MATCH_T &)
2312 struct OrientationLookupTable<2>
2315 std::array<unsigned int, GeometryInfo<2>::vertices_per_face>;
2316 static inline std::bitset<3>
2317 lookup(
const MATCH_T &matching)
2324 static const MATCH_T m_tff = {{0, 1}};
2325 if (matching == m_tff)
2327 static const MATCH_T m_ttf = {{1, 0}};
2328 if (matching == m_ttf)
2338 struct OrientationLookupTable<3>
2341 std::array<unsigned int, GeometryInfo<3>::vertices_per_face>;
2342 static inline std::bitset<3>
2343 lookup(
const MATCH_T &matching)
2350 static const MATCH_T m_tff = {{0, 1, 2, 3}};
2351 if (matching == m_tff)
2353 static const MATCH_T m_tft = {{1, 3, 0, 2}};
2354 if (matching == m_tft)
2356 static const MATCH_T m_ttf = {{3, 2, 1, 0}};
2357 if (matching == m_ttf)
2359 static const MATCH_T m_ttt = {{2, 0, 3, 1}};
2360 if (matching == m_ttt)
2362 static const MATCH_T m_fff = {{0, 2, 1, 3}};
2363 if (matching == m_fff)
2365 static const MATCH_T m_fft = {{2, 3, 0, 1}};
2366 if (matching == m_fft)
2368 static const MATCH_T m_ftf = {{3, 1, 2, 0}};
2369 if (matching == m_ftf)
2371 static const MATCH_T m_ftt = {{1, 0, 3, 2}};
2372 if (matching == m_ftt)
2383 template <
typename FaceIterator>
2385 std::bitset<3> & orientation,
2386 const FaceIterator & face1,
2387 const FaceIterator & face2,
2388 const int direction,
2393 ExcMessage(
"The supplied matrix must be a square matrix"));
2395 static const int dim = FaceIterator::AccessorType::dimension;
2399 std::array<unsigned int, GeometryInfo<dim>::vertices_per_face> matching;
2401 std::set<unsigned int> face2_vertices;
2402 for (
unsigned int i = 0; i < GeometryInfo<dim>::vertices_per_face; ++i)
2403 face2_vertices.insert(i);
2405 for (
unsigned int i = 0; i < GeometryInfo<dim>::vertices_per_face; ++i)
2407 for (std::set<unsigned int>::iterator it = face2_vertices.begin();
2408 it != face2_vertices.end();
2418 face2_vertices.erase(it);
2425 if (face2_vertices.empty())
2426 orientation = OrientationLookupTable<dim>::lookup(matching);
2428 return face2_vertices.empty();
2433 template <
typename FaceIterator>
2436 const FaceIterator & face1,
2437 const FaceIterator & face2,
2438 const int direction,
2443 std::bitset<3> dummy;
2452 #include "grid_tools_dof_handlers.inst" 2455 DEAL_II_NAMESPACE_CLOSE
static const unsigned int invalid_unsigned_int
#define AssertDimension(dim1, dim2)
const std::vector< Point< spacedim > > & get_vertices() const
cell_iterator end() const
SymmetricTensor< 2, dim, Number > e(const Tensor< 2, dim, Number > &F)
const std::vector< bool > & get_used_vertices() const
#define AssertThrow(cond, exc)
virtual Point< dim > transform_real_to_unit_cell(const typename Triangulation< dim, spacedim >::cell_iterator &cell, const Point< spacedim > &p) const =0
static::ExceptionBase & ExcIndexRange(int arg1, int arg2, int arg3)
cell_iterator begin(const unsigned int level=0) const
unsigned int n_active_cells() const
unsigned long long int global_dof_index
static double distance_to_unit_cell(const Point< dim > &p)
typename ActiveSelector::active_cell_iterator active_cell_iterator
virtual void execute_coarsening_and_refinement()
static::ExceptionBase & ExcMessage(std::string arg1)
unsigned int n_cells() const
const Triangulation< dim, spacedim > & get_triangulation() const
virtual void create_triangulation(const std::vector< Point< spacedim >> &vertices, const std::vector< CellData< dim >> &cells, const SubCellData &subcelldata)
#define Assert(cond, exc)
numbers::NumberTraits< Number >::real_type distance_square(const Point< dim, Number > &p) const
static::ExceptionBase & ExcDimensionMismatch(std::size_t arg1, std::size_t arg2)
Abstract base class for mapping classes.
unsigned int size() const
virtual bool preserves_vertex_locations() const =0
static::ExceptionBase & ExcNotImplemented()
const hp::FECollection< dim, spacedim > & get_fe_collection() const
Iterator points to a valid object.
static::ExceptionBase & ExcVertexNotUsed(unsigned int arg1)
active_cell_iterator begin_active(const unsigned int level=0) const
static::ExceptionBase & ExcInternalError()
Triangulation< dim, spacedim > & get_triangulation()