Reference documentation for deal.II version 9.6.0
\(\newcommand{\dealvcentcolon}{\mathrel{\mathop{:}}}\) \(\newcommand{\dealcoloneq}{\dealvcentcolon\mathrel{\mkern-1.2mu}=}\) \(\newcommand{\jump}[1]{\left[\!\left[ #1 \right]\!\right]}\) \(\newcommand{\average}[1]{\left\{\!\left\{ #1 \right\}\!\right\}}\)
Loading...
Searching...
No Matches
grid_tools.h
Go to the documentation of this file.
1// ------------------------------------------------------------------------
2//
3// SPDX-License-Identifier: LGPL-2.1-or-later
4// Copyright (C) 2001 - 2024 by the deal.II authors
5//
6// This file is part of the deal.II library.
7//
8// Part of the source code is dual licensed under Apache-2.0 WITH
9// LLVM-exception OR LGPL-2.1-or-later. Detailed license information
10// governing the source code and code contributions can be found in
11// LICENSE.md and CONTRIBUTING.md at the top level directory of deal.II.
12//
13// ------------------------------------------------------------------------
14
15#ifndef dealii_grid_tools_h
16#define dealii_grid_tools_h
17
18
19#include <deal.II/base/config.h>
20
23#include <deal.II/base/point.h>
24
26
28
30
32#include <deal.II/fe/mapping.h>
33
37#include <deal.II/grid/tria.h>
40
45
47
48#include <boost/archive/binary_iarchive.hpp>
49#include <boost/archive/binary_oarchive.hpp>
50#include <boost/random/mersenne_twister.hpp>
51#include <boost/serialization/array.hpp>
52#include <boost/serialization/vector.hpp>
53
54#ifdef DEAL_II_WITH_ZLIB
55# include <boost/iostreams/device/back_inserter.hpp>
56# include <boost/iostreams/filter/gzip.hpp>
57# include <boost/iostreams/filtering_stream.hpp>
58# include <boost/iostreams/stream.hpp>
59#endif
60
61#include <optional>
62#include <set>
63
64#ifdef DEAL_II_HAVE_CXX20
65# include <concepts>
66#endif
67
68
70
71// Forward declarations
72#ifndef DOXYGEN
73namespace parallel
74{
75 namespace distributed
76 {
77 template <int dim, int spacedim>
79 class Triangulation;
80 }
81} // namespace parallel
82
83namespace hp
84{
85 template <int, int>
86 class MappingCollection;
87}
88
89class SparsityPattern;
90
91namespace GridTools
92{
93 template <int dim, int spacedim>
94 class Cache;
95}
96#endif
97
98namespace internal
99{
100 template <int dim, int spacedim, typename MeshType>
103 {
104 public:
105#ifndef _MSC_VER
106 using type = typename MeshType::active_cell_iterator;
107#else
109#endif
110 };
111
112#ifdef _MSC_VER
113 template <int dim, int spacedim>
114 class ActiveCellIterator<dim, spacedim, DoFHandler<dim, spacedim>>
115 {
116 public:
117 using type =
119 };
120#endif
121} // namespace internal
122
131namespace GridTools
132{
219 template <int dim, typename Transformation, int spacedim>
221 (std::invocable<Transformation, Point<spacedim>> &&
222 std::assignable_from<
224 std::invoke_result_t<Transformation, Point<spacedim>>>))
225 void transform(const Transformation &transformation,
226 Triangulation<dim, spacedim> &triangulation);
227
234 template <int dim, int spacedim>
235 void
236 shift(const Tensor<1, spacedim> &shift_vector,
237 Triangulation<dim, spacedim> &triangulation);
238
239
250 template <int dim, int spacedim>
251 void
252 rotate(const double angle, Triangulation<dim, spacedim> &triangulation);
253
266 template <int dim>
267 void
268 rotate(const Tensor<1, 3, double> &axis,
269 const double angle,
271
287 template <int dim>
289 rotate(const double angle,
290 const unsigned int axis,
292
350 template <int dim>
351 void
352 laplace_transform(const std::map<unsigned int, Point<dim>> &new_points,
353 Triangulation<dim> &tria,
354 const Function<dim, double> *coefficient = nullptr,
355 const bool solve_for_absolute_positions = false);
356
364 template <int dim, int spacedim>
365 void
366 scale(const double scaling_factor,
367 Triangulation<dim, spacedim> &triangulation);
368
398 template <int dim, int spacedim>
399 void
401 const double factor,
402 Triangulation<dim, spacedim> &triangulation,
403 const bool keep_boundary = true,
404 const unsigned int seed = boost::random::mt19937::default_seed);
405
495 template <int dim, int spacedim>
496 void
497 regularize_corner_cells(Triangulation<dim, spacedim> &tria,
498 const double limit_angle_fraction = .75);
499
563 template <int dim, int spacedim>
564#ifndef DOXYGEN
565 std::tuple<
566 std::vector<typename Triangulation<dim, spacedim>::active_cell_iterator>,
567 std::vector<std::vector<Point<dim>>>,
568 std::vector<std::vector<unsigned int>>>
569#else
570 return_type
571#endif
573 const Cache<dim, spacedim> &cache,
574 const std::vector<Point<spacedim>> &points,
576 &cell_hint =
578
612 template <int dim, int spacedim>
613#ifndef DOXYGEN
614 std::tuple<
615 std::vector<typename Triangulation<dim, spacedim>::active_cell_iterator>,
616 std::vector<std::vector<Point<dim>>>,
617 std::vector<std::vector<unsigned int>>,
618 std::vector<unsigned int>>
619#else
620 return_type
621#endif
623 const Cache<dim, spacedim> &cache,
624 const std::vector<Point<spacedim>> &points,
626 &cell_hint =
628
708 template <int dim, int spacedim>
709#ifndef DOXYGEN
710 std::tuple<
711 std::vector<typename Triangulation<dim, spacedim>::active_cell_iterator>,
712 std::vector<std::vector<Point<dim>>>,
713 std::vector<std::vector<unsigned int>>,
714 std::vector<std::vector<Point<spacedim>>>,
715 std::vector<std::vector<unsigned int>>>
716#else
717 return_type
718#endif
721 const std::vector<Point<spacedim>> &local_points,
722 const std::vector<std::vector<BoundingBox<spacedim>>> &global_bboxes,
723 const double tolerance = 1e-10,
724 const std::vector<bool> &marked_vertices = {},
725 const bool enforce_unique_mapping = true);
726
727 namespace internal
728 {
743 template <int dim, int spacedim>
745 {
747
754 void
756
760 unsigned int n_searched_points;
761
768 std::vector<std::tuple<std::pair<int, int>,
769 unsigned int,
770 unsigned int,
773 unsigned int>>
775
779 std::vector<unsigned int> send_ranks;
780
786 std::vector<unsigned int> send_ptrs;
787
798 std::vector<std::tuple<unsigned int, unsigned int, unsigned int>>
800
804 std::vector<unsigned int> recv_ranks;
805
811 std::vector<unsigned int> recv_ptrs;
812 };
813
823 template <int dim, int spacedim>
827 const std::vector<Point<spacedim>> &points,
828 const std::vector<std::vector<BoundingBox<spacedim>>> &global_bboxes,
829 const std::vector<bool> &marked_vertices,
830 const double tolerance,
831 const bool perform_handshake,
832 const bool enforce_unique_mapping = false);
833
834
842 template <int structdim, int spacedim>
844 {
849 std::array<::Point<spacedim>, structdim + 1>;
850
859 std::vector<std::tuple<std::pair<int, int>,
860 unsigned int,
861 unsigned int,
864
873 std::vector<std::tuple<unsigned int, unsigned int, IntersectionType>>
875
879 std::vector<unsigned int> recv_ptrs;
880
901 template <int dim>
903 spacedim>
905 const unsigned int n_points_1D,
907 const Mapping<dim, spacedim> &mapping,
908 std::vector<Quadrature<spacedim>> *mapped_quadratures_recv_comp =
909 nullptr,
910 const bool consistent_numbering_of_sender_and_receiver = false) const;
911
912 private:
920 std::map<unsigned int, std::vector<unsigned int>>
922 const std::vector<std::tuple<unsigned int, unsigned int, unsigned int>>
923 &point_recv_components,
924 const MPI_Comm comm) const;
925 };
926
934 template <int structdim, int dim, int spacedim>
937 const Cache<dim, spacedim> &cache,
938 const std::vector<std::vector<Point<spacedim>>> &intersection_requests,
939 const std::vector<std::vector<BoundingBox<spacedim>>> &global_bboxes,
940 const std::vector<bool> &marked_vertices,
941 const double tolerance);
942
943 } // namespace internal
944
954 template <int spacedim>
955 unsigned int
956 find_closest_vertex(const std::map<unsigned int, Point<spacedim>> &vertices,
957 const Point<spacedim> &p);
958
985 template <int dim, template <int, int> class MeshType, int spacedim>
987 (concepts::is_triangulation_or_dof_handler<MeshType<dim, spacedim>>))
988 unsigned int find_closest_vertex(
989 const MeshType<dim, spacedim> &mesh,
990 const Point<spacedim> &p,
991 const std::vector<bool> &marked_vertices = {});
992
1019 template <int dim, template <int, int> class MeshType, int spacedim>
1021 (concepts::is_triangulation_or_dof_handler<MeshType<dim, spacedim>>))
1022 unsigned int find_closest_vertex(
1023 const Mapping<dim, spacedim> &mapping,
1024 const MeshType<dim, spacedim> &mesh,
1025 const Point<spacedim> &p,
1026 const std::vector<bool> &marked_vertices = {});
1027
1028
1051 template <typename MeshType>
1053#ifndef _MSC_VER
1054 std::vector<typename MeshType::active_cell_iterator>
1055#else
1056 std::vector<
1057 typename ::internal::ActiveCellIterator<MeshType::dimension,
1058 MeshType::space_dimension,
1059 MeshType>::type>
1060#endif
1061 find_cells_adjacent_to_vertex(const MeshType &container,
1062 const unsigned int vertex_index);
1063
1129 template <int dim, template <int, int> class MeshType, int spacedim>
1131 (concepts::is_triangulation_or_dof_handler<MeshType<dim, spacedim>>))
1132#ifndef _MSC_VER
1133 std::pair<typename MeshType<dim, spacedim>::active_cell_iterator, Point<dim>>
1134#else
1135 std::pair<typename ::internal::
1136 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type,
1137 Point<dim>>
1138#endif
1140 const MeshType<dim, spacedim> &mesh,
1141 const Point<spacedim> &p,
1142 const std::vector<bool> &marked_vertices = {},
1143 const double tolerance = 1.e-10);
1144
1155 template <int dim, template <int, int> class MeshType, int spacedim>
1157 (concepts::is_triangulation_or_dof_handler<MeshType<dim, spacedim>>))
1158#ifndef _MSC_VER
1159 typename MeshType<dim, spacedim>::active_cell_iterator
1160#else
1161 typename ::internal::
1162 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type
1163#endif
1164 find_active_cell_around_point(const MeshType<dim, spacedim> &mesh,
1165 const Point<spacedim> &p,
1166 const std::vector<bool> &marked_vertices = {},
1167 const double tolerance = 1.e-10);
1168
1175 template <int dim, int spacedim>
1176 std::pair<typename DoFHandler<dim, spacedim>::active_cell_iterator,
1177 Point<dim>>
1180 const DoFHandler<dim, spacedim> &mesh,
1181 const Point<spacedim> &p,
1182 const double tolerance = 1.e-10);
1183
1235 template <int dim, int spacedim>
1236 std::pair<typename Triangulation<dim, spacedim>::active_cell_iterator,
1237 Point<dim>>
1239 const Cache<dim, spacedim> &cache,
1240 const Point<spacedim> &p,
1243 const std::vector<bool> &marked_vertices = {},
1244 const double tolerance = 1.e-10);
1245
1262 template <int dim, template <int, int> class MeshType, int spacedim>
1264 (concepts::is_triangulation_or_dof_handler<MeshType<dim, spacedim>>))
1265#ifndef _MSC_VER
1266 std::pair<typename MeshType<dim, spacedim>::active_cell_iterator, Point<dim>>
1267#else
1268 std::pair<typename ::internal::
1269 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type,
1270 Point<dim>>
1271#endif
1273 const Mapping<dim, spacedim> &mapping,
1274 const MeshType<dim, spacedim> &mesh,
1275 const Point<spacedim> &p,
1276 const std::vector<
1277 std::set<typename MeshType<dim, spacedim>::active_cell_iterator>>
1279 const std::vector<std::vector<Tensor<1, spacedim>>>
1280 &vertex_to_cell_centers,
1281 const typename MeshType<dim, spacedim>::active_cell_iterator &cell_hint =
1282 typename MeshType<dim, spacedim>::active_cell_iterator(),
1283 const std::vector<bool> &marked_vertices = {},
1284 const RTree<std::pair<Point<spacedim>, unsigned int>> &
1285 used_vertices_rtree = RTree<std::pair<Point<spacedim>, unsigned int>>{},
1286 const double tolerance = 1.e-10,
1287 const RTree<
1288 std::pair<BoundingBox<spacedim>,
1290 *relevant_cell_bounding_boxes_rtree = nullptr);
1291
1321 template <int dim, template <int, int> class MeshType, int spacedim>
1323 (concepts::is_triangulation_or_dof_handler<MeshType<dim, spacedim>>))
1324#ifndef _MSC_VER
1325 std::vector<std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
1326 Point<dim>>>
1327#else
1328 std::vector<std::pair<
1329 typename ::internal::
1330 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type,
1331 Point<dim>>>
1332#endif
1334 const Mapping<dim, spacedim> &mapping,
1335 const MeshType<dim, spacedim> &mesh,
1336 const Point<spacedim> &p,
1337 const double tolerance,
1338 const std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
1339 Point<dim>> &first_cell,
1340 const std::vector<
1341 std::set<typename MeshType<dim, spacedim>::active_cell_iterator>>
1342 *vertex_to_cells = nullptr);
1343
1353 template <int dim, template <int, int> class MeshType, int spacedim>
1355 (concepts::is_triangulation_or_dof_handler<MeshType<dim, spacedim>>))
1356#ifndef _MSC_VER
1357 std::vector<std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
1358 Point<dim>>>
1359#else
1360 std::vector<std::pair<
1361 typename ::internal::
1362 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type,
1363 Point<dim>>>
1364#endif
1366 const Mapping<dim, spacedim> &mapping,
1367 const MeshType<dim, spacedim> &mesh,
1368 const Point<spacedim> &p,
1369 const double tolerance = 1e-10,
1370 const std::vector<bool> &marked_vertices = {});
1371
1395 template <typename MeshType>
1397 std::vector<typename MeshType::active_cell_iterator> get_active_child_cells(
1398 const typename MeshType::cell_iterator &cell);
1399
1426 template <typename MeshType>
1427 DEAL_II_CXX20_REQUIRES(concepts::is_triangulation_or_dof_handler<MeshType>)
1429 const typename MeshType::active_cell_iterator &cell,
1430 std::vector<typename MeshType::active_cell_iterator> &active_neighbors);
1431
1483 template <typename MeshType>
1484 DEAL_II_CXX20_REQUIRES(concepts::is_triangulation_or_dof_handler<MeshType>)
1485 std::
1486 vector<typename MeshType::active_cell_iterator> compute_active_cell_halo_layer(
1487 const MeshType &mesh,
1488 const std::function<bool(const typename MeshType::active_cell_iterator &)>
1489 &predicate);
1490
1491
1501 template <typename MeshType>
1502 DEAL_II_CXX20_REQUIRES(concepts::is_triangulation_or_dof_handler<MeshType>)
1503 std::
1504 vector<typename MeshType::cell_iterator> compute_cell_halo_layer_on_level(
1505 const MeshType &mesh,
1506 const std::function<bool(const typename MeshType::cell_iterator &)>
1507 &predicate,
1508 const unsigned int level);
1509
1510
1525 template <typename MeshType>
1526 DEAL_II_CXX20_REQUIRES(concepts::is_triangulation_or_dof_handler<MeshType>)
1527 std::vector<
1528 typename MeshType::
1529 active_cell_iterator> compute_ghost_cell_halo_layer(const MeshType &mesh);
1530
1581 template <typename MeshType>
1582 DEAL_II_CXX20_REQUIRES(concepts::is_triangulation_or_dof_handler<MeshType>)
1583 std::
1584 vector<typename MeshType::active_cell_iterator> compute_active_cell_layer_within_distance(
1585 const MeshType &mesh,
1586 const std::function<bool(const typename MeshType::active_cell_iterator &)>
1587 &predicate,
1588 const double layer_thickness);
1589
1614 template <typename MeshType>
1615 DEAL_II_CXX20_REQUIRES(concepts::is_triangulation_or_dof_handler<MeshType>)
1616 std::
1617 vector<typename MeshType::active_cell_iterator> compute_ghost_cell_layer_within_distance(
1618 const MeshType &mesh,
1619 const double layer_thickness);
1620
1693 template <typename MeshType>
1694 DEAL_II_CXX20_REQUIRES(concepts::is_triangulation_or_dof_handler<MeshType>)
1695 std::
1696 vector<BoundingBox<MeshType::space_dimension>> compute_mesh_predicate_bounding_box(
1697 const MeshType &mesh,
1698 const std::function<bool(const typename MeshType::active_cell_iterator &)>
1699 &predicate,
1700 const unsigned int refinement_level = 0,
1701 const bool allow_merge = false,
1702 const unsigned int max_boxes = numbers::invalid_unsigned_int);
1703
1731 template <int spacedim>
1732#ifndef DOXYGEN
1733 std::tuple<std::vector<std::vector<unsigned int>>,
1734 std::map<unsigned int, unsigned int>,
1735 std::map<unsigned int, std::vector<unsigned int>>>
1736#else
1737 return_type
1738#endif
1740 const std::vector<std::vector<BoundingBox<spacedim>>> &global_bboxes,
1741 const std::vector<Point<spacedim>> &points);
1742
1743
1778 template <int spacedim>
1779#ifndef DOXYGEN
1780 std::tuple<std::map<unsigned int, std::vector<unsigned int>>,
1781 std::map<unsigned int, unsigned int>,
1782 std::map<unsigned int, std::vector<unsigned int>>>
1783#else
1784 return_type
1785#endif
1787 const RTree<std::pair<BoundingBox<spacedim>, unsigned int>> &covering_rtree,
1788 const std::vector<Point<spacedim>> &points);
1789
1802 template <int dim, int spacedim>
1803 std::vector<std::vector<Tensor<1, spacedim>>>
1805 const Triangulation<dim, spacedim> &mesh,
1806 const std::vector<
1808 &vertex_to_cells);
1809
1810
1818 template <int dim, int spacedim>
1819 unsigned int
1822 const Point<spacedim> &position,
1823 const Mapping<dim, spacedim> &mapping =
1825#ifndef _MSC_VER
1827#else
1829#endif
1830 ));
1831
1843 template <int dim, int spacedim>
1844 std::map<unsigned int, types::global_vertex_index>
1847
1874 template <int dim, int spacedim>
1875 void
1876 partition_triangulation(const unsigned int n_partitions,
1878 const SparsityTools::Partitioner partitioner =
1880
1891 template <int dim, int spacedim>
1892 void
1893 partition_triangulation(const unsigned int n_partitions,
1894 const std::vector<unsigned int> &cell_weights,
1896 const SparsityTools::Partitioner partitioner =
1898
1944 template <int dim, int spacedim>
1945 void
1946 partition_triangulation(const unsigned int n_partitions,
1947 const SparsityPattern &cell_connection_graph,
1949 const SparsityTools::Partitioner partitioner =
1951
1962 template <int dim, int spacedim>
1963 void
1964 partition_triangulation(const unsigned int n_partitions,
1965 const std::vector<unsigned int> &cell_weights,
1966 const SparsityPattern &cell_connection_graph,
1968 const SparsityTools::Partitioner partitioner =
1970
1985 template <int dim, int spacedim>
1986 void
1987 partition_triangulation_zorder(const unsigned int n_partitions,
1989 const bool group_siblings = true);
1990
2002 template <int dim, int spacedim>
2003 void
2005
2013 template <int dim, int spacedim>
2014 std::vector<types::subdomain_id>
2016 const std::vector<CellId> &cell_ids);
2017
2028 template <int dim, int spacedim>
2029 void
2031 std::vector<types::subdomain_id> &subdomain);
2032
2047 template <int dim, int spacedim>
2048 unsigned int
2051 const types::subdomain_id subdomain);
2052
2082 template <int dim, int spacedim>
2083 std::vector<bool>
2085
2112 template <int dim, int spacedim>
2116 &distorted_cells,
2118
2119
2120
2170 template <typename MeshType>
2172 std::vector<typename MeshType::active_cell_iterator> get_patch_around_cell(
2173 const typename MeshType::active_cell_iterator &cell);
2174
2175
2197 template <class Container>
2198 std::vector<typename Container::cell_iterator>
2200 const std::vector<typename Container::active_cell_iterator> &patch_cells);
2201
2268 template <class Container>
2269 void
2271 const std::vector<typename Container::active_cell_iterator> &patch,
2273 &local_triangulation,
2274 std::map<
2275 typename Triangulation<Container::dimension,
2276 Container::space_dimension>::active_cell_iterator,
2277 typename Container::active_cell_iterator> &patch_to_global_tria_map);
2278
2310 template <int dim, int spacedim>
2311 std::map<
2313 std::vector<typename DoFHandler<dim, spacedim>::active_cell_iterator>>
2315
2316
2331 template <typename CellIterator>
2333 {
2337 CellIterator cell[2];
2338
2343 unsigned int face_idx[2];
2344
2350 unsigned char orientation;
2351
2365
2369 std::size_t
2371 };
2372
2373
2395 template <typename FaceIterator>
2396 std::optional<unsigned char>
2398 const FaceIterator &face1,
2399 const FaceIterator &face2,
2400 const unsigned int direction,
2403 const FullMatrix<double> &matrix = FullMatrix<double>());
2404
2463 template <typename MeshType>
2466 const MeshType &mesh,
2467 const types::boundary_id b_id1,
2468 const types::boundary_id b_id2,
2469 const unsigned int direction,
2471 &matched_pairs,
2474 const FullMatrix<double> &matrix = FullMatrix<double>());
2475
2476
2501 template <typename MeshType>
2504 const MeshType &mesh,
2505 const types::boundary_id b_id,
2506 const unsigned int direction,
2507 std::vector<PeriodicFacePair<typename MeshType::cell_iterator>>
2508 &matched_pairs,
2509 const ::Tensor<1, MeshType::space_dimension> &offset =
2510 ::Tensor<1, MeshType::space_dimension>(),
2511 const FullMatrix<double> &matrix = FullMatrix<double>());
2512
2539 template <int dim, int spacedim>
2540 void
2541 copy_boundary_to_manifold_id(Triangulation<dim, spacedim> &tria,
2542 const bool reset_boundary_ids = false);
2543
2565 template <int dim, int spacedim>
2566 void
2568 const std::vector<types::boundary_id> &src_boundary_ids,
2569 const std::vector<types::manifold_id> &dst_manifold_ids,
2570 Triangulation<dim, spacedim> &tria,
2571 const std::vector<types::boundary_id> &reset_boundary_ids = {});
2572
2602 template <int dim, int spacedim>
2603 void
2605 const bool compute_face_ids = false);
2606
2631 template <int dim, int spacedim>
2632 void
2635 const std::function<types::manifold_id(
2636 const std::set<types::manifold_id> &)> &disambiguation_function =
2637 [](const std::set<types::manifold_id> &manifold_ids) {
2638 if (manifold_ids.size() == 1)
2639 return *manifold_ids.begin();
2640 else
2642 },
2643 bool overwrite_only_flat_manifold_ids = true);
2732 template <typename DataType, typename MeshType>
2735 const MeshType &mesh,
2736 const std::function<std::optional<DataType>(
2737 const typename MeshType::active_cell_iterator &)> &pack,
2738 const std::function<void(const typename MeshType::active_cell_iterator &,
2739 const DataType &)> &unpack,
2740 const std::function<bool(const typename MeshType::active_cell_iterator &)>
2741 &cell_filter =
2742 always_return<typename MeshType::active_cell_iterator, bool>{true});
2743
2756 template <typename DataType, typename MeshType>
2759 const MeshType &mesh,
2760 const std::function<std::optional<DataType>(
2761 const typename MeshType::level_cell_iterator &)> &pack,
2762 const std::function<void(const typename MeshType::level_cell_iterator &,
2763 const DataType &)> &unpack,
2764 const std::function<bool(const typename MeshType::level_cell_iterator &)> &
2765 cell_filter = always_return<typename MeshType::level_cell_iterator, bool>{
2766 true});
2767
2768 /* Exchange with all processors of the MPI communicator @p mpi_communicator the vector of bounding
2769 * boxes @p local_bboxes.
2770 *
2771 * This function is meant to exchange bounding boxes describing the locally
2772 * owned cells in a distributed triangulation obtained with the function
2773 * GridTools::compute_mesh_predicate_bounding_box .
2774 *
2775 * The output vector's size is the number of processes of the MPI
2776 * communicator:
2777 * its i-th entry contains the vector @p local_bboxes of the i-th process.
2778 */
2779 template <int spacedim>
2780 std::vector<std::vector<BoundingBox<spacedim>>>
2782 const std::vector<BoundingBox<spacedim>> &local_bboxes,
2783 const MPI_Comm mpi_communicator);
2784
2817 template <int spacedim>
2820 const std::vector<BoundingBox<spacedim>> &local_description,
2821 const MPI_Comm mpi_communicator);
2822
2840 template <int dim, int spacedim>
2841 void
2843 const Triangulation<dim, spacedim> &tria,
2844 std::map<unsigned int, std::vector<unsigned int>> &coinciding_vertex_groups,
2845 std::map<unsigned int, unsigned int> &vertex_to_coinciding_vertex_group);
2846
2866 template <int dim, int spacedim>
2867 std::map<unsigned int, std::set<::types::subdomain_id>>
2869 const Triangulation<dim, spacedim> &tria);
2870
2891 template <int dim, typename VectorType>
2893 {
2894 public:
2898 using value_type = typename VectorType::value_type;
2899
2904 const FiniteElement<dim, dim> &fe,
2905 const unsigned int n_subdivisions = 1,
2906 const double tolerance = 1e-10);
2907
2918 void
2919 process(const DoFHandler<dim> &background_dof_handler,
2920 const VectorType &ls_vector,
2921 const double iso_level,
2922 std::vector<Point<dim>> &vertices,
2923 std::vector<CellData<dim == 1 ? 1 : dim - 1>> &cells) const;
2924
2929 void
2930 process(const DoFHandler<dim> &background_dof_handler,
2931 const VectorType &ls_vector,
2932 const double iso_level,
2933 std::vector<Point<dim>> &vertices) const;
2934
2944 void
2946 const VectorType &ls_vector,
2947 const double iso_level,
2948 std::vector<Point<dim>> &vertices,
2949 std::vector<CellData<dim == 1 ? 1 : dim - 1>> &cells) const;
2955 void
2957 const VectorType &ls_vector,
2958 const double iso_level,
2959 std::vector<Point<dim>> &vertices) const;
2960
2961 private:
2966 static Quadrature<dim>
2967 create_quadrature_rule(const unsigned int n_subdivisions);
2968
2972 void
2973 process_cell(std::vector<value_type> &ls_values,
2974 const std::vector<Point<dim>> &points,
2975 const double iso_level,
2976 std::vector<Point<dim>> &vertices,
2977 std::vector<CellData<dim == 1 ? 1 : dim - 1>> &cells,
2978 const bool write_back_cell_data = true) const;
2979
2983 void
2984 process_sub_cell(const std::vector<value_type> &,
2985 const std::vector<Point<1>> &,
2986 const std::vector<unsigned int> &,
2987 const double,
2988 std::vector<Point<1>> &,
2989 std::vector<CellData<1>> &,
2990 const bool) const
2991 {
2993 }
2994
3001 void
3002 process_sub_cell(const std::vector<value_type> &ls_values,
3003 const std::vector<Point<2>> &points,
3004 const std::vector<unsigned int> &mask,
3005 const double iso_level,
3006 std::vector<Point<2>> &vertices,
3007 std::vector<CellData<1>> &cells,
3008 const bool write_back_cell_data) const;
3009
3013 void
3014 process_sub_cell(const std::vector<value_type> &ls_values,
3015 const std::vector<Point<3>> &points,
3016 const std::vector<unsigned int> &mask,
3017 const double iso_level,
3018 std::vector<Point<3>> &vertices,
3019 std::vector<CellData<2>> &cells,
3020 const bool write_back_cell_data) const;
3021
3026 const unsigned int n_subdivisions;
3027
3032 const double tolerance;
3033
3039 };
3040
3041
3042
3052 int,
3053 << "The number of partitions you gave is " << arg1
3054 << ", but must be greater than zero.");
3059 int,
3060 << "The subdomain id " << arg1
3061 << " has no cells associated with it.");
3066
3071 double,
3072 << "The scaling factor must be positive, but it is " << arg1
3073 << '.');
3074
3079 unsigned int,
3080 << "The given vertex with index " << arg1
3081 << " is not used in the given triangulation.");
3082
3085} /*namespace GridTools*/
3086
3087/* ----------------- Template function --------------- */
3088
3089#ifndef DOXYGEN
3090
3091namespace GridTools
3092{
3093 template <int dim>
3094 double
3096 const std::vector<Point<dim>> &all_vertices,
3097 const unsigned int (&indices)[GeometryInfo<dim>::vertices_per_cell])
3098 {
3099 // We forward call to the ArrayView version:
3102 return cell_measure(all_vertices, view);
3103 }
3104
3105
3106
3107 // This specialization is defined here so that the general template in the
3108 // source file doesn't need to have further 1d overloads for the internal
3109 // functions it calls.
3110 template <>
3114 {
3115 return {};
3116 }
3117
3118
3119
3120 template <int dim, typename Transformation, int spacedim>
3122 (std::invocable<Transformation, Point<spacedim>> &&
3123 std::assignable_from<
3125 std::invoke_result_t<Transformation, Point<spacedim>>>))
3126 void transform(const Transformation &transformation,
3127 Triangulation<dim, spacedim> &triangulation)
3128 {
3129 std::vector<bool> treated_vertices(triangulation.n_vertices(), false);
3130
3131 // loop over all active cells, and
3132 // transform those vertices that
3133 // have not yet been touched. note
3134 // that we get to all vertices in
3135 // the triangulation by only
3136 // visiting the active cells.
3138 cell = triangulation.begin_active(),
3139 endc = triangulation.end();
3140 for (; cell != endc; ++cell)
3141 for (const unsigned int v : cell->vertex_indices())
3142 if (treated_vertices[cell->vertex_index(v)] == false)
3143 {
3144 // transform this vertex
3145 cell->vertex(v) = transformation(cell->vertex(v));
3146 // and mark it as treated
3147 treated_vertices[cell->vertex_index(v)] = true;
3148 };
3149
3150
3151 // now fix any vertices on hanging nodes so that we don't create any holes
3152 if (dim == 2)
3153 {
3155 cell = triangulation.begin_active(),
3156 endc = triangulation.end();
3157 for (; cell != endc; ++cell)
3158 for (const unsigned int face : cell->face_indices())
3159 if (cell->face(face)->has_children() &&
3160 !cell->face(face)->at_boundary())
3161 {
3162 Assert(cell->reference_cell() ==
3165
3166 // this line has children
3167 cell->face(face)->child(0)->vertex(1) =
3168 (cell->face(face)->vertex(0) + cell->face(face)->vertex(1)) /
3169 2;
3170 }
3171 }
3172 else if (dim == 3)
3173 {
3175 cell = triangulation.begin_active(),
3176 endc = triangulation.end();
3177 for (; cell != endc; ++cell)
3178 for (const unsigned int face : cell->face_indices())
3179 if (cell->face(face)->has_children() &&
3180 !cell->face(face)->at_boundary())
3181 {
3182 Assert(cell->reference_cell() ==
3185
3186 // this face has hanging nodes
3187 cell->face(face)->child(0)->vertex(1) =
3188 (cell->face(face)->vertex(0) + cell->face(face)->vertex(1)) /
3189 2.0;
3190 cell->face(face)->child(0)->vertex(2) =
3191 (cell->face(face)->vertex(0) + cell->face(face)->vertex(2)) /
3192 2.0;
3193 cell->face(face)->child(1)->vertex(3) =
3194 (cell->face(face)->vertex(1) + cell->face(face)->vertex(3)) /
3195 2.0;
3196 cell->face(face)->child(2)->vertex(3) =
3197 (cell->face(face)->vertex(2) + cell->face(face)->vertex(3)) /
3198 2.0;
3199
3200 // center of the face
3201 cell->face(face)->child(0)->vertex(3) =
3202 (cell->face(face)->vertex(0) + cell->face(face)->vertex(1) +
3203 cell->face(face)->vertex(2) + cell->face(face)->vertex(3)) /
3204 4.0;
3205 }
3206 }
3207
3208 // Make sure FEValues notices that the mesh has changed
3209 triangulation.signals.mesh_movement();
3210 }
3211
3212
3213
3214 template <typename MeshType>
3216 std::vector<typename MeshType::active_cell_iterator> get_active_child_cells(
3217 const typename MeshType::cell_iterator &cell)
3218 {
3219 std::vector<typename MeshType::active_cell_iterator> child_cells;
3220
3221 if (cell->has_children())
3222 {
3223 for (unsigned int child = 0; child < cell->n_children(); ++child)
3224 if (cell->child(child)->has_children())
3225 {
3226 const std::vector<typename MeshType::active_cell_iterator>
3227 children = get_active_child_cells<MeshType>(cell->child(child));
3228 child_cells.insert(child_cells.end(),
3229 children.begin(),
3230 children.end());
3231 }
3232 else
3233 child_cells.push_back(cell->child(child));
3234 }
3235
3236 return child_cells;
3237 }
3238
3239
3240
3241 template <typename MeshType>
3244 const typename MeshType::active_cell_iterator &cell,
3245 std::vector<typename MeshType::active_cell_iterator> &active_neighbors)
3246 {
3247 active_neighbors.clear();
3248 for (const unsigned int n : cell->face_indices())
3249 if (!cell->at_boundary(n))
3250 {
3251 if (MeshType::dimension == 1)
3252 {
3253 // check children of neighbor. note
3254 // that in 1d children of the neighbor
3255 // may be further refined. In 1d the
3256 // case is simple since we know what
3257 // children bound to the present cell
3258 typename MeshType::cell_iterator neighbor_child =
3259 cell->neighbor(n);
3260 if (!neighbor_child->is_active())
3261 {
3262 while (neighbor_child->has_children())
3263 neighbor_child = neighbor_child->child(n == 0 ? 1 : 0);
3264
3265 Assert(neighbor_child->neighbor(n == 0 ? 1 : 0) == cell,
3267 }
3268 active_neighbors.push_back(neighbor_child);
3269 }
3270 else
3271 {
3272 if (cell->face(n)->has_children())
3273 // this neighbor has children. find
3274 // out which border to the present
3275 // cell
3276 for (unsigned int c = 0;
3277 c < cell->face(n)->n_active_descendants();
3278 ++c)
3279 active_neighbors.push_back(
3280 cell->neighbor_child_on_subface(n, c));
3281 else
3282 {
3283 // the neighbor must be active
3284 // himself
3285 Assert(cell->neighbor(n)->is_active(), ExcInternalError());
3286 active_neighbors.push_back(cell->neighbor(n));
3287 }
3288 }
3289 }
3290 }
3291
3292
3293
3294 template <typename CellIterator>
3295 std::size_t
3297 {
3298 return sizeof(*this) + matrix.memory_consumption();
3299 }
3300
3301
3302
3303 namespace internal
3304 {
3305 template <typename DataType,
3306 typename MeshType,
3307 typename MeshCellIteratorType>
3309 inline void exchange_cell_data(
3310 const MeshType &mesh,
3311 const std::function<std::optional<DataType>(const MeshCellIteratorType &)>
3312 &pack,
3313 const std::function<void(const MeshCellIteratorType &, const DataType &)>
3314 &unpack,
3315 const std::function<bool(const MeshCellIteratorType &)> &cell_filter,
3316 const std::function<void(
3317 const std::function<void(const MeshCellIteratorType &,
3318 const types::subdomain_id)> &)> &process_cells,
3319 const std::function<std::set<types::subdomain_id>(
3320 const parallel::TriangulationBase<MeshType::dimension,
3321 MeshType::space_dimension> &)>
3322 &compute_ghost_owners)
3323 {
3324# ifndef DEAL_II_WITH_MPI
3325 (void)mesh;
3326 (void)pack;
3327 (void)unpack;
3328 (void)cell_filter;
3329 (void)process_cells;
3330 (void)compute_ghost_owners;
3331 Assert(false, ExcNeedsMPI());
3332# else
3333 constexpr int dim = MeshType::dimension;
3334 constexpr int spacedim = MeshType::space_dimension;
3335 auto tria =
3336 dynamic_cast<const parallel::TriangulationBase<dim, spacedim> *>(
3337 &mesh.get_triangulation());
3338 Assert(
3339 tria != nullptr,
3340 ExcMessage(
3341 "The function exchange_cell_data_to_ghosts() only works with parallel triangulations."));
3342
3343 if (const auto tria = dynamic_cast<
3345 &mesh.get_triangulation()))
3346 {
3347 Assert(
3348 tria->with_artificial_cells(),
3349 ExcMessage(
3350 "The functions GridTools::exchange_cell_data_to_ghosts() and "
3351 "GridTools::exchange_cell_data_to_level_ghosts() can only "
3352 "operate on a single layer of ghost cells. However, you have "
3353 "given a Triangulation object of type "
3354 "parallel::shared::Triangulation without artificial cells "
3355 "resulting in an arbitrary number of ghost layers. "
3356 "To use this function for a Triangulation object of type "
3357 "parallel::shared::Triangulation, make sure to create the "
3358 "Triangulation object with allow_artificial_cells set to true. "
3359 "This results in a parallel::shared::Triangulation with only "
3360 "a single layer of ghost cells."));
3361 }
3362
3363 // build list of cells to request for each neighbor
3364 std::set<::types::subdomain_id> ghost_owners =
3365 compute_ghost_owners(*tria);
3366 std::map<::types::subdomain_id,
3367 std::vector<typename CellId::binary_type>>
3368 neighbor_cell_list;
3369
3370 for (const auto ghost_owner : ghost_owners)
3371 neighbor_cell_list[ghost_owner] = {};
3372
3373 process_cells([&](const auto &cell, const auto key) -> void {
3374 if (cell_filter(cell))
3375 {
3376 constexpr int spacedim = MeshType::space_dimension;
3377 neighbor_cell_list[key].emplace_back(
3378 cell->id().template to_binary<spacedim>());
3379 }
3380 });
3381
3382 Assert(ghost_owners.size() == neighbor_cell_list.size(),
3384
3385
3386 // Before sending & receiving, make sure we protect this section with
3387 // a mutex:
3390 mutex, tria->get_communicator());
3391
3392 const int mpi_tag =
3394 const int mpi_tag_reply =
3396
3397 // send our requests
3398 std::vector<MPI_Request> requests(ghost_owners.size());
3399 {
3400 unsigned int idx = 0;
3401 for (const auto &it : neighbor_cell_list)
3402 {
3403 // send the data about the relevant cells
3404 const int ierr = MPI_Isend(it.second.data(),
3405 it.second.size() * sizeof(it.second[0]),
3406 MPI_BYTE,
3407 it.first,
3408 mpi_tag,
3409 tria->get_communicator(),
3410 &requests[idx]);
3411 AssertThrowMPI(ierr);
3412 ++idx;
3413 }
3414 }
3415
3416 // receive requests and reply with the results
3417 std::vector<MPI_Request> reply_requests(ghost_owners.size());
3418 std::vector<std::vector<char>> sendbuffers(ghost_owners.size());
3419
3420 for (unsigned int idx = 0; idx < ghost_owners.size(); ++idx)
3421 {
3422 MPI_Status status;
3423 int ierr = MPI_Probe(MPI_ANY_SOURCE,
3424 mpi_tag,
3425 tria->get_communicator(),
3426 &status);
3427 AssertThrowMPI(ierr);
3428
3429 int len;
3430 ierr = MPI_Get_count(&status, MPI_BYTE, &len);
3431 AssertThrowMPI(ierr);
3432 Assert(len % sizeof(typename CellId::binary_type) == 0,
3434
3435 const unsigned int n_cells =
3436 len / sizeof(typename CellId::binary_type);
3437 std::vector<typename CellId::binary_type> cells_with_requests(
3438 n_cells);
3439 std::vector<DataType> data_to_send;
3440 data_to_send.reserve(n_cells);
3441 std::vector<bool> cell_carries_data(n_cells, false);
3442
3443 ierr = MPI_Recv(cells_with_requests.data(),
3444 len,
3445 MPI_BYTE,
3446 status.MPI_SOURCE,
3447 status.MPI_TAG,
3448 tria->get_communicator(),
3449 &status);
3450 AssertThrowMPI(ierr);
3451
3452 // store data for each cell
3453 for (unsigned int c = 0; c < static_cast<unsigned int>(n_cells); ++c)
3454 {
3455 const auto cell =
3456 tria->create_cell_iterator(CellId(cells_with_requests[c]));
3457
3458 MeshCellIteratorType mesh_it(tria,
3459 cell->level(),
3460 cell->index(),
3461 &mesh);
3462
3463 const std::optional<DataType> data = pack(mesh_it);
3464 if (data)
3465 {
3466 data_to_send.emplace_back(*data);
3467 cell_carries_data[c] = true;
3468 }
3469 }
3470
3471 // collect data for sending the reply in a buffer
3472
3473 // (a) make room for storing the local offsets in case we receive
3474 // other data
3475 sendbuffers[idx].resize(sizeof(std::size_t));
3476
3477 // (b) append the actual data and store how much memory it
3478 // corresponds to, which we then insert into the leading position of
3479 // the sendbuffer
3480 std::size_t size_of_send =
3481 Utilities::pack(data_to_send,
3482 sendbuffers[idx],
3483 /*enable_compression*/ false);
3484 std::memcpy(sendbuffers[idx].data(),
3485 &size_of_send,
3486 sizeof(std::size_t));
3487
3488 // (c) append information of certain cells that got left out in case
3489 // we need it
3490 if (data_to_send.size() < n_cells)
3491 Utilities::pack(cell_carries_data,
3492 sendbuffers[idx],
3493 /*enable_compression*/ false);
3494
3495 // send data
3496 ierr = MPI_Isend(sendbuffers[idx].data(),
3497 sendbuffers[idx].size(),
3498 MPI_BYTE,
3499 status.MPI_SOURCE,
3500 mpi_tag_reply,
3501 tria->get_communicator(),
3502 &reply_requests[idx]);
3503 AssertThrowMPI(ierr);
3504 }
3505
3506 // finally receive the replies
3507 std::vector<char> receive;
3508 for (unsigned int id = 0; id < neighbor_cell_list.size(); ++id)
3509 {
3510 MPI_Status status;
3511 int ierr = MPI_Probe(MPI_ANY_SOURCE,
3512 mpi_tag_reply,
3513 tria->get_communicator(),
3514 &status);
3515 AssertThrowMPI(ierr);
3516
3517 int len;
3518 ierr = MPI_Get_count(&status, MPI_BYTE, &len);
3519 AssertThrowMPI(ierr);
3520
3521 receive.resize(len);
3522
3523 ierr = MPI_Recv(receive.data(),
3524 len,
3525 MPI_BYTE,
3526 status.MPI_SOURCE,
3527 status.MPI_TAG,
3528 tria->get_communicator(),
3529 &status);
3530 AssertThrowMPI(ierr);
3531
3532 // (a) first determine the length of the data section in the
3533 // received buffer
3534 auto data_iterator = receive.begin();
3535 std::size_t size_of_received_data =
3536 Utilities::unpack<std::size_t>(data_iterator,
3537 data_iterator + sizeof(std::size_t));
3538 data_iterator += sizeof(std::size_t);
3539
3540 // (b) unpack the data section in the indicated region
3541 auto received_data = Utilities::unpack<std::vector<DataType>>(
3542 data_iterator,
3543 data_iterator + size_of_received_data,
3544 /*enable_compression*/ false);
3545 data_iterator += size_of_received_data;
3546
3547 // (c) check if the received data contained fewer entries than the
3548 // number of cells we identified in the beginning, in which case we
3549 // need to extract the boolean vector with the relevant information
3550 const std::vector<typename CellId::binary_type> &this_cell_list =
3551 neighbor_cell_list[status.MPI_SOURCE];
3552 AssertIndexRange(received_data.size(), this_cell_list.size() + 1);
3553 std::vector<bool> cells_with_data;
3554 if (received_data.size() < this_cell_list.size())
3555 {
3556 cells_with_data = Utilities::unpack<std::vector<bool>>(
3557 data_iterator, receive.end(), /*enable_compression*/ false);
3558 AssertDimension(cells_with_data.size(), this_cell_list.size());
3559 }
3560
3561 // (d) go through the received data and call the user-provided
3562 // unpack function
3563 auto received_data_iterator = received_data.begin();
3564 for (unsigned int c = 0; c < this_cell_list.size(); ++c)
3565 if (cells_with_data.empty() || cells_with_data[c])
3566 {
3568 tria_cell = tria->create_cell_iterator(this_cell_list[c]);
3569
3570 MeshCellIteratorType cell(tria,
3571 tria_cell->level(),
3572 tria_cell->index(),
3573 &mesh);
3574
3575 unpack(cell, *received_data_iterator);
3576 ++received_data_iterator;
3577 }
3578 }
3579
3580 // make sure that all communication is finished
3581 // when we leave this function.
3582 if (requests.size() > 0)
3583 {
3584 const int ierr =
3585 MPI_Waitall(requests.size(), requests.data(), MPI_STATUSES_IGNORE);
3586 AssertThrowMPI(ierr);
3587 }
3588 if (reply_requests.size() > 0)
3589 {
3590 const int ierr = MPI_Waitall(reply_requests.size(),
3591 reply_requests.data(),
3592 MPI_STATUSES_IGNORE);
3593 AssertThrowMPI(ierr);
3594 }
3595
3596
3597# endif // DEAL_II_WITH_MPI
3598 }
3599
3600 } // namespace internal
3601
3602 template <typename DataType, typename MeshType>
3604 inline void exchange_cell_data_to_ghosts(
3605 const MeshType &mesh,
3606 const std::function<std::optional<DataType>(
3607 const typename MeshType::active_cell_iterator &)> &pack,
3608 const std::function<void(const typename MeshType::active_cell_iterator &,
3609 const DataType &)> &unpack,
3610 const std::function<bool(const typename MeshType::active_cell_iterator &)>
3611 &cell_filter)
3612 {
3613# ifndef DEAL_II_WITH_MPI
3614 (void)mesh;
3615 (void)pack;
3616 (void)unpack;
3617 (void)cell_filter;
3618 Assert(false, ExcNeedsMPI());
3619# else
3620 internal::exchange_cell_data<DataType,
3621 MeshType,
3622 typename MeshType::active_cell_iterator>(
3623 mesh,
3624 pack,
3625 unpack,
3626 cell_filter,
3627 [&](const auto &process) {
3628 for (const auto &cell : mesh.active_cell_iterators())
3629 if (cell->is_ghost())
3630 process(cell, cell->subdomain_id());
3631 },
3632 [](const auto &tria) { return tria.ghost_owners(); });
3633# endif
3634 }
3635
3636
3637
3638 template <typename DataType, typename MeshType>
3641 const MeshType &mesh,
3642 const std::function<std::optional<DataType>(
3643 const typename MeshType::level_cell_iterator &)> &pack,
3644 const std::function<void(const typename MeshType::level_cell_iterator &,
3645 const DataType &)> &unpack,
3646 const std::function<bool(const typename MeshType::level_cell_iterator &)>
3647 &cell_filter)
3648 {
3649# ifndef DEAL_II_WITH_MPI
3650 (void)mesh;
3651 (void)pack;
3652 (void)unpack;
3653 (void)cell_filter;
3654 Assert(false, ExcNeedsMPI());
3655# else
3656 internal::exchange_cell_data<DataType,
3657 MeshType,
3658 typename MeshType::level_cell_iterator>(
3659 mesh,
3660 pack,
3661 unpack,
3662 cell_filter,
3663 [&](const auto &process) {
3664 for (const auto &cell : mesh.cell_iterators())
3665 if (cell->is_ghost_on_level())
3666 process(cell, cell->level_subdomain_id());
3667 },
3668 [](const auto &tria) { return tria.level_ghost_owners(); });
3669# endif
3670 }
3671} // namespace GridTools
3672
3673#endif // DOXYGEN
3674
3676
3677#endif
std::array< unsigned int, 4 > binary_type
Definition cell_id.h:80
typename VectorType::value_type value_type
const unsigned int n_subdivisions
MarchingCubeAlgorithm(const Mapping< dim, dim > &mapping, const FiniteElement< dim, dim > &fe, const unsigned int n_subdivisions=1, const double tolerance=1e-10)
static Quadrature< dim > create_quadrature_rule(const unsigned int n_subdivisions)
void process_cell(const typename DoFHandler< dim >::active_cell_iterator &cell, const VectorType &ls_vector, const double iso_level, std::vector< Point< dim > > &vertices, std::vector< CellData< dim==1 ? 1 :dim - 1 > > &cells) const
void process_sub_cell(const std::vector< value_type > &, const std::vector< Point< 1 > > &, const std::vector< unsigned int > &, const double, std::vector< Point< 1 > > &, std::vector< CellData< 1 > > &, const bool) const
void process(const DoFHandler< dim > &background_dof_handler, const VectorType &ls_vector, const double iso_level, std::vector< Point< dim > > &vertices, std::vector< CellData< dim==1 ? 1 :dim - 1 > > &cells) const
Abstract base class for mapping classes.
Definition mapping.h:318
Definition point.h:111
const Mapping< dim, spacedim > & get_default_linear_mapping() const
virtual MPI_Comm get_communicator() const
cell_iterator create_cell_iterator(const CellId &cell_id) const
cell_iterator end() const
Signals signals
Definition tria.h:2513
unsigned int n_vertices() const
active_cell_iterator begin_active(const unsigned int level=0) const
typename MeshType::active_cell_iterator type
Definition grid_tools.h:106
#define DEAL_II_DEPRECATED
Definition config.h:207
#define DEAL_II_NAMESPACE_OPEN
Definition config.h:503
#define DEAL_II_CXX20_REQUIRES(condition)
Definition config.h:177
#define DEAL_II_NAMESPACE_CLOSE
Definition config.h:504
Point< 3 > vertices[4]
unsigned int level
Definition grid_out.cc:4626
unsigned int vertex_indices[2]
#define DeclException0(Exception0)
Definition exceptions.h:471
static ::ExceptionBase & ExcNotImplemented()
static ::ExceptionBase & ExcNeedsMPI()
static ::ExceptionBase & ExcNonExistentSubdomain(int arg1)
#define Assert(cond, exc)
static ::ExceptionBase & ExcVertexNotUsed(unsigned int arg1)
#define AssertDimension(dim1, dim2)
#define AssertThrowMPI(error_code)
#define AssertIndexRange(index, range)
static ::ExceptionBase & ExcInternalError()
static ::ExceptionBase & ExcTriangulationHasBeenRefined()
#define DeclException1(Exception1, type1, outsequence)
Definition exceptions.h:516
static ::ExceptionBase & ExcInvalidNumberOfPartitions(int arg1)
static ::ExceptionBase & ExcMessage(std::string arg1)
static ::ExceptionBase & ExcScalingFactorNotPositive(double arg1)
#define AssertThrow(cond, exc)
typename ActiveSelector::active_cell_iterator active_cell_iterator
void copy_boundary_to_manifold_id(Triangulation< dim, spacedim > &tria, const bool reset_boundary_ids=false)
void copy_material_to_manifold_id(Triangulation< dim, spacedim > &tria, const bool compute_face_ids=false)
void map_boundary_to_manifold_ids(const std::vector< types::boundary_id > &src_boundary_ids, const std::vector< types::manifold_id > &dst_manifold_ids, Triangulation< dim, spacedim > &tria, const std::vector< types::boundary_id > &reset_boundary_ids={})
void assign_co_dimensional_manifold_indicators(Triangulation< dim, spacedim > &tria, const std::function< types::manifold_id(const std::set< types::manifold_id > &)> &disambiguation_function=[](const std::set< types::manifold_id > &manifold_ids) { if(manifold_ids.size()==1) return *manifold_ids.begin();else return numbers::flat_manifold_id;}, bool overwrite_only_flat_manifold_ids=true)
const Mapping< dim, spacedim > & get_default_linear_mapping(const Triangulation< dim, spacedim > &triangulation)
Definition mapping.cc:294
DistributedComputePointLocationsInternal< dim, spacedim > distributed_compute_point_locations(const GridTools::Cache< dim, spacedim > &cache, const std::vector< Point< spacedim > > &points, const std::vector< std::vector< BoundingBox< spacedim > > > &global_bboxes, const std::vector< bool > &marked_vertices, const double tolerance, const bool perform_handshake, const bool enforce_unique_mapping=false)
DistributedComputeIntersectionLocationsInternal< structdim, spacedim > distributed_compute_intersection_locations(const Cache< dim, spacedim > &cache, const std::vector< std::vector< Point< spacedim > > > &intersection_requests, const std::vector< std::vector< BoundingBox< spacedim > > > &global_bboxes, const std::vector< bool > &marked_vertices, const double tolerance)
std::vector< BoundingBox< MeshType::space_dimension > > compute_mesh_predicate_bounding_box(const MeshType &mesh, const std::function< bool(const typename MeshType::active_cell_iterator &)> &predicate, const unsigned int refinement_level=0, const bool allow_merge=false, const unsigned int max_boxes=numbers::invalid_unsigned_int)
void scale(const double scaling_factor, Triangulation< dim, spacedim > &triangulation)
RTree< std::pair< BoundingBox< spacedim >, unsigned int > > build_global_description_tree(const std::vector< BoundingBox< spacedim > > &local_description, const MPI_Comm mpi_communicator)
std::vector< typename MeshType::active_cell_iterator > get_active_child_cells(const typename MeshType::cell_iterator &cell)
void partition_triangulation_zorder(const unsigned int n_partitions, Triangulation< dim, spacedim > &triangulation, const bool group_siblings=true)
Triangulation< dim, spacedim >::DistortedCellList fix_up_distorted_child_cells(const typename Triangulation< dim, spacedim >::DistortedCellList &distorted_cells, Triangulation< dim, spacedim > &triangulation)
std::vector< typename Container::cell_iterator > get_cells_at_coarsest_common_level(const std::vector< typename Container::active_cell_iterator > &patch_cells)
void rotate(const double angle, Triangulation< dim, spacedim > &triangulation)
return_type compute_point_locations(const Cache< dim, spacedim > &cache, const std::vector< Point< spacedim > > &points, const typename Triangulation< dim, spacedim >::active_cell_iterator &cell_hint=typename Triangulation< dim, spacedim >::active_cell_iterator())
unsigned int find_closest_vertex(const std::map< unsigned int, Point< spacedim > > &vertices, const Point< spacedim > &p)
void transform(const Transformation &transformation, Triangulation< dim, spacedim > &triangulation)
unsigned int find_closest_vertex_of_cell(const typename Triangulation< dim, spacedim >::active_cell_iterator &cell, const Point< spacedim > &position, const Mapping< dim, spacedim > &mapping=(ReferenceCells::get_hypercube< dim >() .template get_default_linear_mapping< dim, spacedim >()))
std::pair< typename MeshType< dim, spacedim >::active_cell_iterator, Point< dim > > find_active_cell_around_point(const Mapping< dim, spacedim > &mapping, const MeshType< dim, spacedim > &mesh, const Point< spacedim > &p, const std::vector< bool > &marked_vertices={}, const double tolerance=1.e-10)
void get_active_neighbors(const typename MeshType::active_cell_iterator &cell, std::vector< typename MeshType::active_cell_iterator > &active_neighbors)
std::vector< bool > get_locally_owned_vertices(const Triangulation< dim, spacedim > &triangulation)
void regularize_corner_cells(Triangulation< dim, spacedim > &tria, const double limit_angle_fraction=.75)
void shift(const Tensor< 1, spacedim > &shift_vector, Triangulation< dim, spacedim > &triangulation)
std::vector< typename MeshType::active_cell_iterator > find_cells_adjacent_to_vertex(const MeshType &container, const unsigned int vertex_index)
std::vector< typename MeshType::active_cell_iterator > compute_active_cell_halo_layer(const MeshType &mesh, const std::function< bool(const typename MeshType::active_cell_iterator &)> &predicate)
void exchange_cell_data_to_level_ghosts(const MeshType &mesh, const std::function< std::optional< DataType >(const typename MeshType::level_cell_iterator &)> &pack, const std::function< void(const typename MeshType::level_cell_iterator &, const DataType &)> &unpack, const std::function< bool(const typename MeshType::level_cell_iterator &)> &cell_filter=always_return< typename MeshType::level_cell_iterator, bool >{ true})
std::vector< typename MeshType::active_cell_iterator > compute_active_cell_layer_within_distance(const MeshType &mesh, const std::function< bool(const typename MeshType::active_cell_iterator &)> &predicate, const double layer_thickness)
std::map< unsigned int, types::global_vertex_index > compute_local_to_global_vertex_index_map(const Triangulation< dim, spacedim > &triangulation)
std::vector< typename MeshType::active_cell_iterator > compute_ghost_cell_halo_layer(const MeshType &mesh)
void collect_periodic_faces(const MeshType &mesh, const types::boundary_id b_id1, const types::boundary_id b_id2, const unsigned int direction, std::vector< PeriodicFacePair< typename MeshType::cell_iterator > > &matched_pairs, const Tensor< 1, MeshType::space_dimension > &offset=::Tensor< 1, MeshType::space_dimension >(), const FullMatrix< double > &matrix=FullMatrix< double >())
void exchange_cell_data_to_ghosts(const MeshType &mesh, const std::function< std::optional< DataType >(const typename MeshType::active_cell_iterator &)> &pack, const std::function< void(const typename MeshType::active_cell_iterator &, const DataType &)> &unpack, const std::function< bool(const typename MeshType::active_cell_iterator &)> &cell_filter=always_return< typename MeshType::active_cell_iterator, bool >{true})
void laplace_transform(const std::map< unsigned int, Point< dim > > &new_points, Triangulation< dim > &tria, const Function< dim, double > *coefficient=nullptr, const bool solve_for_absolute_positions=false)
void partition_multigrid_levels(Triangulation< dim, spacedim > &triangulation)
std::optional< unsigned char > orthogonal_equality(const FaceIterator &face1, const FaceIterator &face2, const unsigned int direction, const Tensor< 1, FaceIterator::AccessorType::space_dimension > &offset=Tensor< 1, FaceIterator::AccessorType::space_dimension >(), const FullMatrix< double > &matrix=FullMatrix< double >())
std::map< unsigned int, std::set<::types::subdomain_id > > compute_vertices_with_ghost_neighbors(const Triangulation< dim, spacedim > &tria)
void collect_coinciding_vertices(const Triangulation< dim, spacedim > &tria, std::map< unsigned int, std::vector< unsigned int > > &coinciding_vertex_groups, std::map< unsigned int, unsigned int > &vertex_to_coinciding_vertex_group)
unsigned int count_cells_with_subdomain_association(const Triangulation< dim, spacedim > &triangulation, const types::subdomain_id subdomain)
return_type guess_point_owner(const std::vector< std::vector< BoundingBox< spacedim > > > &global_bboxes, const std::vector< Point< spacedim > > &points)
std::map< types::global_dof_index, std::vector< typename DoFHandler< dim, spacedim >::active_cell_iterator > > get_dof_to_support_patch_map(DoFHandler< dim, spacedim > &dof_handler)
std::vector< typename MeshType::cell_iterator > compute_cell_halo_layer_on_level(const MeshType &mesh, const std::function< bool(const typename MeshType::cell_iterator &)> &predicate, const unsigned int level)
void partition_triangulation(const unsigned int n_partitions, Triangulation< dim, spacedim > &triangulation, const SparsityTools::Partitioner partitioner=SparsityTools::Partitioner::metis)
std::vector< std::set< typename Triangulation< dim, spacedim >::active_cell_iterator > > vertex_to_cell_map(const Triangulation< dim, spacedim > &triangulation)
std::vector< typename MeshType::active_cell_iterator > compute_ghost_cell_layer_within_distance(const MeshType &mesh, const double layer_thickness)
return_type compute_point_locations_try_all(const Cache< dim, spacedim > &cache, const std::vector< Point< spacedim > > &points, const typename Triangulation< dim, spacedim >::active_cell_iterator &cell_hint=typename Triangulation< dim, spacedim >::active_cell_iterator())
std::vector< typename MeshType::active_cell_iterator > get_patch_around_cell(const typename MeshType::active_cell_iterator &cell)
std::vector< types::subdomain_id > get_subdomain_association(const Triangulation< dim, spacedim > &triangulation, const std::vector< CellId > &cell_ids)
void distort_random(const double factor, Triangulation< dim, spacedim > &triangulation, const bool keep_boundary=true, const unsigned int seed=boost::random::mt19937::default_seed)
std::vector< std::vector< Tensor< 1, spacedim > > > vertex_to_cell_centers_directions(const Triangulation< dim, spacedim > &mesh, const std::vector< std::set< typename Triangulation< dim, spacedim >::active_cell_iterator > > &vertex_to_cells)
std::vector< std::pair< typename MeshType< dim, spacedim >::active_cell_iterator, Point< dim > > > find_all_active_cells_around_point(const Mapping< dim, spacedim > &mapping, const MeshType< dim, spacedim > &mesh, const Point< spacedim > &p, const double tolerance, const std::pair< typename MeshType< dim, spacedim >::active_cell_iterator, Point< dim > > &first_cell, const std::vector< std::set< typename MeshType< dim, spacedim >::active_cell_iterator > > *vertex_to_cells=nullptr)
void build_triangulation_from_patch(const std::vector< typename Container::active_cell_iterator > &patch, Triangulation< Container::dimension, Container::space_dimension > &local_triangulation, std::map< typename Triangulation< Container::dimension, Container::space_dimension >::active_cell_iterator, typename Container::active_cell_iterator > &patch_to_global_tria_map)
std::vector< std::vector< BoundingBox< spacedim > > > exchange_local_bounding_boxes(const std::vector< BoundingBox< spacedim > > &local_bboxes, const MPI_Comm mpi_communicator)
double cell_measure(const std::vector< Point< dim > > &all_vertices, const ArrayView< const unsigned int > &vertex_indices)
return_type distributed_compute_point_locations(const GridTools::Cache< dim, spacedim > &cache, const std::vector< Point< spacedim > > &local_points, const std::vector< std::vector< BoundingBox< spacedim > > > &global_bboxes, const double tolerance=1e-10, const std::vector< bool > &marked_vertices={}, const bool enforce_unique_mapping=true)
@ matrix
Contents is actually a matrix.
constexpr const ReferenceCell & get_hypercube()
@ exchange_cell_data_request
grid_tools.h: exchange_cell_ghosts()
Definition mpi_tags.h:65
@ exchange_cell_data_reply
grid_tools.h: exchange_cell_ghosts()
Definition mpi_tags.h:68
size_t pack(const T &object, std::vector< char > &dest_buffer, const bool allow_compression=true)
Definition utilities.h:1381
T unpack(const std::vector< char > &buffer, const bool allow_compression=true)
Definition utilities.h:1538
Definition hp.h:117
unsigned int n_cells(const internal::TriangulationImplementation::NumberCache< 1 > &c)
Definition tria.cc:14883
const types::manifold_id flat_manifold_id
Definition types.h:325
STL namespace.
Definition types.h:32
unsigned int boundary_id
Definition types.h:144
unsigned int subdomain_id
Definition types.h:43
unsigned int global_dof_index
Definition types.h:81
const ::parallel::distributed::Triangulation< dim, spacedim > * triangulation
*braid_SplitCommworld & comm
boost::geometry::index::rtree< LeafType, IndexType, IndexableGetter > RTree
Definition rtree.h:144
std::size_t memory_consumption() const
FullMatrix< double > matrix
std::map< unsigned int, std::vector< unsigned int > > communicate_indices(const std::vector< std::tuple< unsigned int, unsigned int, unsigned int > > &point_recv_components, const MPI_Comm comm) const
std::array<::Point< spacedim >, structdim+1 > IntersectionType
Definition grid_tools.h:848
GridTools::internal::DistributedComputePointLocationsInternal< dim, spacedim > convert_to_distributed_compute_point_locations_internal(const unsigned int n_points_1D, const Triangulation< dim, spacedim > &tria, const Mapping< dim, spacedim > &mapping, std::vector< Quadrature< spacedim > > *mapped_quadratures_recv_comp=nullptr, const bool consistent_numbering_of_sender_and_receiver=false) const
std::vector< std::tuple< std::pair< int, int >, unsigned int, unsigned int, IntersectionType > > send_components
Definition grid_tools.h:863
std::vector< std::tuple< unsigned int, unsigned int, IntersectionType > > recv_components
Definition grid_tools.h:874
std::vector< std::tuple< unsigned int, unsigned int, unsigned int > > recv_components
Definition grid_tools.h:799
std::vector< std::tuple< std::pair< int, int >, unsigned int, unsigned int, Point< dim >, Point< spacedim >, unsigned int > > send_components
Definition grid_tools.h:774