16#ifndef dealii_grid_tools_h
17#define dealii_grid_tools_h
49#include <boost/archive/binary_iarchive.hpp>
50#include <boost/archive/binary_oarchive.hpp>
51#include <boost/random/mersenne_twister.hpp>
52#include <boost/serialization/array.hpp>
53#include <boost/serialization/vector.hpp>
55#ifdef DEAL_II_WITH_ZLIB
56# include <boost/iostreams/device/back_inserter.hpp>
57# include <boost/iostreams/filter/gzip.hpp>
58# include <boost/iostreams/filtering_stream.hpp>
59# include <boost/iostreams/stream.hpp>
66#ifdef DEAL_II_HAVE_CXX20
79 template <
int dim,
int spacedim>
88 class MappingCollection;
95 template <
int dim,
int spacedim>
102 template <
int dim,
int spacedim,
class MeshType>
108 using type =
typename MeshType::active_cell_iterator;
115 template <
int dim,
int spacedim>
146 template <
int dim,
int spacedim>
173 template <
int dim,
int spacedim>
204 template <
int dim,
int spacedim>
219 template <
int dim,
int spacedim>
224 (ReferenceCells::get_hypercube<dim>()
226 .
template get_default_linear_mapping<dim, spacedim>()
228 .ReferenceCell::get_default_linear_mapping<dim, spacedim>()
242 template <
int dim,
int spacedim>
247 (ReferenceCells::get_hypercube<dim>()
249 .
template get_default_linear_mapping<dim, spacedim>()
251 .ReferenceCell::get_default_linear_mapping<dim, spacedim>()
318 template <
int dim,
int spacedim>
383 template <
int dim,
int spacedim>
404 template <
typename Iterator>
407 const Iterator &
object,
422 template <
int dim,
int spacedim>
424 tuple<std::vector<Point<spacedim>>, std::vector<CellData<dim>>,
SubCellData>
449 template <
int dim,
int spacedim>
473 template <
int dim,
int spacedim>
478 std::vector<unsigned int> & considered_vertices,
479 const double tol = 1e-12);
491 const double tol = 1e-12);
511 template <
int dim,
int spacedim>
526 template <
int dim,
int spacedim>
633 template <
int dim,
typename Transformation,
int spacedim>
636 std::assignable_from<
648 template <
int dim,
int spacedim>
664 template <
int dim,
int spacedim>
703 rotate(const
double angle,
704 const
unsigned int axis,
768 const
Function<dim,
double> *coefficient =
nullptr,
769 const
bool solve_for_absolute_positions = false);
776 template <
int dim,
int spacedim>
777 std::map<
unsigned int,
Point<spacedim>>
787 template <
int dim,
int spacedim>
789 scale(const
double scaling_factor,
811 template <
int dim,
int spacedim>
816 const
bool keep_boundary = true,
817 const
unsigned int seed =
boost::random::mt19937::default_seed);
852 template <
int dim,
int spacedim>
855 const
bool isotropic = false,
856 const
unsigned int max_iterations = 100);
882 template <
int dim,
int spacedim>
885 const
double max_ratio = 1.6180339887,
886 const
unsigned int max_iterations = 5);
977 template <
int dim,
int spacedim>
980 const
double limit_angle_fraction = .75);
1045 template <
int dim,
int spacedim>
1048 std::vector<typename Triangulation<dim, spacedim>::active_cell_iterator>,
1049 std::vector<std::vector<Point<dim>>>,
1050 std::vector<std::vector<unsigned int>>>
1094 template <
int dim,
int spacedim>
1097 std::vector<typename Triangulation<dim, spacedim>::active_cell_iterator>,
1098 std::vector<std::vector<Point<dim>>>,
1099 std::vector<std::vector<unsigned int>>,
1100 std::vector<unsigned int>>
1190 template <
int dim,
int spacedim>
1193 std::vector<typename Triangulation<dim, spacedim>::active_cell_iterator>,
1194 std::vector<std::vector<Point<dim>>>,
1195 std::vector<std::vector<unsigned int>>,
1196 std::vector<std::vector<Point<spacedim>>>,
1197 std::vector<std::vector<unsigned int>>>
1205 const double tolerance = 1e-10,
1206 const std::vector<bool> & marked_vertices = {},
1207 const bool enforce_unique_mapping =
true);
1225 template <
int dim,
int spacedim>
1250 std::vector<std::tuple<std::pair<int, int>,
1280 std::vector<std::tuple<unsigned int, unsigned int, unsigned int>>
1305 template <
int dim,
int spacedim>
1311 const std::vector<bool> & marked_vertices,
1312 const double tolerance,
1313 const bool perform_handshake,
1314 const bool enforce_unique_mapping =
false);
1324 template <
int structdim,
int spacedim>
1331 std::array<::Point<spacedim>, structdim + 1>;
1341 std::vector<std::tuple<std::pair<int, int>,
1355 std::vector<std::tuple<unsigned int, unsigned int, IntersectionType>>
1382 const unsigned int n_points_1D,
1385 const bool consistent_numbering_of_sender_and_receiver =
false)
const;
1395 std::map<unsigned int, std::vector<unsigned int>>
1397 const std::vector<std::tuple<unsigned int, unsigned int, unsigned int>>
1398 & point_recv_components,
1409 template <
int structdim,
int dim,
int spacedim>
1413 const std::vector<std::vector<
Point<spacedim>>> &intersection_requests,
1415 const std::vector<bool> & marked_vertices,
1416 const double tolerance);
1456 template <
int dim,
int spacedim>
1457 std::map<unsigned int, Point<spacedim>>
1461 (ReferenceCells::get_hypercube<dim>()
1463 .
template get_default_linear_mapping<dim, spacedim>()
1465 .ReferenceCell::get_default_linear_mapping<dim, spacedim>()
1478 template <
int spacedim>
1509 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
1513 const MeshType<dim, spacedim> &mesh,
1514 const
Point<spacedim> & p,
1515 const
std::vector<
bool> & marked_vertices = {});
1543 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
1547 const
Mapping<dim, spacedim> & mapping,
1548 const MeshType<dim, spacedim> &mesh,
1549 const
Point<spacedim> & p,
1550 const
std::vector<
bool> & marked_vertices = {});
1575 template <
class MeshType>
1578 std::vector<typename MeshType::active_cell_iterator>
1581 typename ::internal::ActiveCellIterator<MeshType::dimension,
1582 MeshType::space_dimension,
1586 const unsigned int vertex_index);
1653 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
1657 std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
Point<dim>>
1659 std::pair<typename ::internal::
1660 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type,
1664 const MeshType<dim, spacedim> &mesh,
1666 const std::vector<bool> &marked_vertices = {},
1667 const double tolerance = 1.e-10);
1679 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
1683 typename MeshType<dim, spacedim>::active_cell_iterator
1685 typename ::internal::
1686 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type
1690 const std::vector<bool> &marked_vertices = {},
1691 const double tolerance = 1.e-10);
1699 template <
int dim,
int spacedim>
1700 std::pair<typename DoFHandler<dim, spacedim>::active_cell_iterator,
1706 const double tolerance = 1.e-10);
1759 template <
int dim,
int spacedim>
1760 std::pair<typename Triangulation<dim, spacedim>::active_cell_iterator,
1763 const Cache<dim, spacedim> &cache,
1767 const std::vector<bool> &marked_vertices = {},
1768 const double tolerance = 1.e-10);
1786 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
1790 std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
Point<dim>>
1792 std::pair<typename ::internal::
1793 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type,
1798 const MeshType<dim, spacedim> &mesh,
1801 std::set<
typename MeshType<dim, spacedim>::active_cell_iterator>>
1804 &vertex_to_cell_centers,
1805 const typename MeshType<dim, spacedim>::active_cell_iterator &cell_hint =
1806 typename MeshType<dim, spacedim>::active_cell_iterator(),
1807 const std::vector<bool> &marked_vertices = {},
1810 const double tolerance = 1.e-10,
1812 std::pair<BoundingBox<spacedim>,
1814 *relevant_cell_bounding_boxes_rtree =
nullptr);
1840 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
1844 std::vector<std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
1847 std::vector<std::pair<
1848 typename ::internal::
1849 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type,
1854 const MeshType<dim, spacedim> &mesh,
1856 const double tolerance,
1857 const std::pair<
typename MeshType<dim, spacedim>::active_cell_iterator,
1869 template <
int dim,
template <
int,
int>
class MeshType,
int spacedim>
1873 std::vector<std::pair<typename MeshType<dim, spacedim>::active_cell_iterator,
1876 std::vector<std::pair<
1877 typename ::internal::
1878 ActiveCellIterator<dim, spacedim, MeshType<dim, spacedim>>::type,
1883 const MeshType<dim, spacedim> &mesh,
1885 const double tolerance = 1e-10,
1886 const std::vector<bool> & marked_vertices = {});
1911 template <
class MeshType>
1914 const typename MeshType::cell_iterator &cell);
1942 template <class MeshType>
1945 const typename MeshType::active_cell_iterator & cell,
1946 std::vector<typename MeshType::active_cell_iterator> &active_neighbors);
1999 template <class MeshType>
2003 const MeshType &mesh,
2004 const
std::function<
bool(const typename MeshType::active_cell_iterator &)>
2017 template <class MeshType>
2021 const MeshType &mesh,
2022 const
std::function<
bool(const typename MeshType::cell_iterator &)>
2024 const
unsigned int level);
2041 template <class MeshType>
2097 template <class MeshType>
2101 const MeshType &mesh,
2102 const
std::function<
bool(const typename MeshType::active_cell_iterator &)>
2104 const
double layer_thickness);
2130 template <class MeshType>
2134 const MeshType &mesh,
2135 const
double layer_thickness);
2154 template <class MeshType>
2157 Point<MeshType::space_dimension>,
2160 const
std::function<
bool(
2161 const typename MeshType::
2162 active_cell_iterator &)>
2237 template <class MeshType>
2241 const MeshType &mesh,
2242 const
std::function<
bool(const typename MeshType::active_cell_iterator &)>
2244 const
unsigned int refinement_level = 0,
2245 const
bool allow_merge = false,
2246 const
unsigned int max_boxes =
numbers::invalid_unsigned_int);
2275 template <
int spacedim>
2277 std::tuple<std::vector<std::vector<unsigned int>>,
2278 std::map<unsigned int, unsigned int>,
2279 std::map<unsigned int, std::vector<unsigned int>>>
2322 template <
int spacedim>
2324 std::tuple<std::map<unsigned int, std::vector<unsigned int>>,
2325 std::map<unsigned int, unsigned int>,
2326 std::map<unsigned int, std::vector<unsigned int>>>
2343 template <
int dim,
int spacedim>
2345 std::set<typename Triangulation<dim, spacedim>::active_cell_iterator>>
2360 template <
int dim,
int spacedim>
2361 std::vector<std::vector<Tensor<1, spacedim>>>
2376 template <
int dim,
int spacedim>
2382 (ReferenceCells::get_hypercube<dim>()
2384 .
template get_default_linear_mapping<dim, spacedim>()
2386 .ReferenceCell::get_default_linear_mapping<dim, spacedim>()
2401 template <
int dim,
int spacedim>
2402 std::map<unsigned int, types::global_vertex_index>
2417 template <
int dim,
int spacedim>
2418 std::pair<unsigned int, double>
2436 template <
int dim,
int spacedim>
2450 template <
int dim,
int spacedim>
2464 template <
int dim,
int spacedim>
2468 const unsigned int level,
2491 template <
int dim,
int spacedim>
2508 template <
int dim,
int spacedim>
2511 const std::vector<unsigned int> &cell_weights,
2561 template <
int dim,
int spacedim>
2579 template <
int dim,
int spacedim>
2582 const std::vector<unsigned int> &cell_weights,
2602 template <
int dim,
int spacedim>
2606 const bool group_siblings =
true);
2619 template <
int dim,
int spacedim>
2630 template <
int dim,
int spacedim>
2631 std::vector<types::subdomain_id>
2633 const std::vector<CellId> & cell_ids);
2645 template <
int dim,
int spacedim>
2648 std::vector<types::subdomain_id> & subdomain);
2664 template <
int dim,
int spacedim>
2699 template <
int dim,
int spacedim>
2744 template <
typename MeshType>
2746 std::list<std::pair<
2747 typename MeshType::cell_iterator,
2762 template <
int dim,
int spacedim>
2778 template <
typename MeshType>
2803 template <
int dim,
int spacedim>
2861 template <
class MeshType>
2864 const typename MeshType::active_cell_iterator &cell);
2888 template <
class Container>
2889 std::vector<typename Container::cell_iterator>
2891 const std::vector<typename Container::active_cell_iterator> &patch_cells);
2959 template <
class Container>
2962 const std::vector<typename Container::active_cell_iterator> &patch,
2964 &local_triangulation,
2967 Container::space_dimension>::active_cell_iterator,
2968 typename Container::active_cell_iterator> &patch_to_global_tria_map);
3001 template <
int dim,
int spacedim>
3004 std::vector<typename DoFHandler<dim, spacedim>::active_cell_iterator>>
3020 template <
typename CellIterator>
3126 template <
typename FaceIterator>
3129 std::bitset<3> & orientation,
3130 const FaceIterator & face1,
3131 const FaceIterator & face2,
3132 const unsigned int direction,
3141 template <
typename FaceIterator>
3144 const FaceIterator & face1,
3145 const FaceIterator & face2,
3146 const unsigned int direction,
3210 template <
typename MeshType>
3213 const MeshType & mesh,
3216 const unsigned int direction,
3248 template <
typename MeshType>
3251 const MeshType & mesh,
3252 const
types::boundary_id b_id,
3253 const
unsigned int direction,
3256 const ::
Tensor<1, MeshType::space_dimension> &offset =
3257 ::
Tensor<1, MeshType::space_dimension>(),
3286 template <
int dim,
int spacedim>
3289 const
bool reset_boundary_ids = false);
3312 template <
int dim,
int spacedim>
3315 const
std::vector<
types::boundary_id> &src_boundary_ids,
3316 const
std::vector<
types::manifold_id> &dst_manifold_ids,
3318 const
std::vector<
types::boundary_id> &reset_boundary_ids = {});
3349 template <
int dim,
int spacedim>
3352 const bool compute_face_ids =
false);
3378 template <
int dim,
int spacedim>
3383 const std::set<types::manifold_id> &)> &disambiguation_function =
3384 [](
const std::set<types::manifold_id> &manifold_ids) {
3385 if (manifold_ids.size() == 1)
3386 return *manifold_ids.begin();
3390 bool overwrite_only_flat_manifold_ids =
true);
3479 template <
typename DataType,
typename MeshType>
3482 const MeshType & mesh,
3484 const typename MeshType::active_cell_iterator &)> &pack,
3485 const
std::function<
void(const typename MeshType::active_cell_iterator &,
3486 const DataType &)> & unpack,
3487 const
std::function<
bool(const typename MeshType::active_cell_iterator &)>
3489 always_return<typename MeshType::active_cell_iterator,
bool>{
true});
3503 template <
typename DataType,
typename MeshType>
3506 const MeshType & mesh,
3508 const typename MeshType::level_cell_iterator &)> &pack,
3509 const
std::function<
void(const typename MeshType::level_cell_iterator &,
3510 const DataType &)> & unpack,
3511 const
std::function<
bool(const typename MeshType::level_cell_iterator &)> &
3512 cell_filter =
always_return<typename MeshType::level_cell_iterator,
bool>{
3526 template <
int spacedim>
3527 std::vector<std::vector<BoundingBox<spacedim>>>
3564 template <
int spacedim>
3587 template <
int dim,
int spacedim>
3613 template <
int dim,
int spacedim>
3614 std::map<unsigned int, std::set<::types::subdomain_id>>
3633 template <
int dim,
typename T>
3654 template <
class Archive>
3656 save(Archive &ar,
const unsigned int)
const
3660 Assert(cell_ids.size() == data.size(),
3663 const std::size_t n_cells = cell_ids.size();
3665 for (
const auto &
id : cell_ids)
3668 ar & binary_cell_id;
3680 template <
class Archive>
3682 load(Archive &ar,
const unsigned int)
3686 std::size_t n_cells;
3689 cell_ids.reserve(n_cells);
3690 for (
unsigned int c = 0; c < n_cells; ++c)
3694 cell_ids.emplace_back(value);
3706 template <
class Archive>
3712 BOOST_SERIALIZATION_SPLIT_MEMBER()
3738 template <
int dim,
typename VectorType>
3767 const VectorType & ls_vector,
3768 const double iso_level,
3778 const VectorType & ls_vector,
3779 const double iso_level,
3793 const VectorType & ls_vector,
3794 const double iso_level,
3804 const VectorType & ls_vector,
3805 const double iso_level,
3822 const double iso_level,
3825 const bool write_back_cell_data =
true)
const;
3833 const std::vector<unsigned int> &,
3850 const std::vector<
Point<2>> & points,
3851 const std::vector<unsigned int> &mask,
3852 const double iso_level,
3855 const bool write_back_cell_data)
const;
3862 const std::vector<
Point<3>> & points,
3863 const std::vector<unsigned int> &mask,
3864 const double iso_level,
3867 const bool write_back_cell_data)
const;
3900 <<
"The number of partitions you gave is " << arg1
3901 <<
", but must be greater than zero.");
3907 <<
"The subdomain id " << arg1
3908 <<
" has no cells associated with it.");
3919 <<
"The scaling factor must be positive, but it is " << arg1
3927 <<
"The given vertex with index " << arg1
3928 <<
" is not used in the given triangulation.");
3945 "The edges of the mesh are not consistently orientable.");
3982 template <
int dim,
typename Transformation,
int spacedim>
3985 std::assignable_from<
3988 void
transform(const Transformation & transformation,
3991 std::vector<bool> treated_vertices(
triangulation.n_vertices(),
false);
4002 for (; cell != endc; ++cell)
4004 if (treated_vertices[cell->vertex_index(v)] == false)
4007 cell->vertex(v) = transformation(cell->vertex(v));
4009 treated_vertices[cell->vertex_index(v)] =
true;
4019 for (; cell != endc; ++cell)
4020 for (
const unsigned int face : cell->face_indices())
4021 if (cell->face(face)->has_children() &&
4022 !cell->face(face)->at_boundary())
4024 Assert(cell->reference_cell() ==
4025 ReferenceCells::get_hypercube<dim>(),
4029 cell->face(face)->child(0)->vertex(1) =
4030 (cell->face(face)->vertex(0) + cell->face(face)->vertex(1)) /
4039 for (; cell != endc; ++cell)
4040 for (
const unsigned int face : cell->face_indices())
4041 if (cell->face(face)->has_children() &&
4042 !cell->face(face)->at_boundary())
4044 Assert(cell->reference_cell() ==
4045 ReferenceCells::get_hypercube<dim>(),
4049 cell->face(face)->child(0)->vertex(1) =
4050 (cell->face(face)->vertex(0) + cell->face(face)->vertex(1)) /
4052 cell->face(face)->child(0)->vertex(2) =
4053 (cell->face(face)->vertex(0) + cell->face(face)->vertex(2)) /
4055 cell->face(face)->child(1)->vertex(3) =
4056 (cell->face(face)->vertex(1) + cell->face(face)->vertex(3)) /
4058 cell->face(face)->child(2)->vertex(3) =
4059 (cell->face(face)->vertex(2) + cell->face(face)->vertex(3)) /
4063 cell->face(face)->child(0)->vertex(3) =
4064 (cell->face(face)->vertex(0) + cell->face(face)->vertex(1) +
4065 cell->face(face)->vertex(2) + cell->face(face)->vertex(3)) /
4076 template <
class MeshType>
4079 const typename MeshType::cell_iterator &cell)
4081 std::vector<typename MeshType::active_cell_iterator> child_cells;
4083 if (cell->has_children())
4085 for (
unsigned int child = 0; child < cell->n_children(); ++child)
4086 if (cell->child(child)->has_children())
4088 const std::vector<typename MeshType::active_cell_iterator>
4089 children = get_active_child_cells<MeshType>(cell->child(child));
4090 child_cells.insert(child_cells.end(),
4095 child_cells.push_back(cell->child(child));
4103 template <
class MeshType>
4106 const typename MeshType::active_cell_iterator & cell,
4107 std::vector<typename MeshType::active_cell_iterator> &active_neighbors)
4109 active_neighbors.clear();
4110 for (
const unsigned int n : cell->face_indices())
4111 if (!cell->at_boundary(n))
4113 if (MeshType::dimension == 1)
4120 typename MeshType::cell_iterator neighbor_child =
4122 if (!neighbor_child->is_active())
4124 while (neighbor_child->has_children())
4125 neighbor_child = neighbor_child->child(n == 0 ? 1 : 0);
4127 Assert(neighbor_child->neighbor(n == 0 ? 1 : 0) == cell,
4130 active_neighbors.push_back(neighbor_child);
4134 if (cell->face(n)->has_children())
4138 for (
unsigned int c = 0;
4139 c < cell->face(n)->n_active_descendants();
4141 active_neighbors.push_back(
4142 cell->neighbor_child_on_subface(n, c));
4148 active_neighbors.push_back(cell->neighbor(n));
4156 template <
typename CellIterator>
4160 return sizeof(*this) +
matrix.memory_consumption();
4167 namespace ProjectToObject
4181 struct CrossDerivative
4183 const unsigned int direction_0;
4184 const unsigned int direction_1;
4186 CrossDerivative(
const unsigned int d0,
const unsigned int d1);
4189 inline CrossDerivative::CrossDerivative(
const unsigned int d0,
4190 const unsigned int d1)
4201 template <
typename F>
4203 centered_first_difference(
const double center,
4207 return (f(
center + step) - f(
center - step)) / (2.0 * step);
4216 template <
typename F>
4218 centered_second_difference(
const double center,
4237 template <
int structdim,
typename F>
4240 const CrossDerivative cross_derivative,
4246 simplex_vector[cross_derivative.direction_0] = 0.5 * step;
4247 simplex_vector[cross_derivative.direction_1] = -0.5 * step;
4248 return (-4.0 * f(
center) - 1.0 * f(
center + simplex_vector) -
4249 1.0 / 3.0 * f(
center - simplex_vector) +
4250 16.0 / 3.0 * f(
center + 0.5 * simplex_vector)) /
4262 template <
int spacedim,
int structdim,
typename F>
4265 const unsigned int row_n,
4266 const unsigned int dependent_direction,
4273 dependent_direction <
4275 ExcMessage(
"This function assumes that the last weight is a "
4276 "dependent variable (and hence we cannot take its "
4277 "derivative directly)."));
4278 Assert(row_n != dependent_direction,
4280 "We cannot differentiate with respect to the variable "
4281 "that is assumed to be dependent."));
4285 {row_n, dependent_direction},
center, step, f);
4287 for (
unsigned int dim_n = 0; dim_n < spacedim; ++dim_n)
4289 -2.0 * (p0[dim_n] - manifold_point[dim_n]) * stencil_value[dim_n];
4298 template <
typename Iterator,
int spacedim,
int structdim>
4300 project_to_d_linear_object(
const Iterator &
object,
4336 for (
unsigned int d = 0;
d < structdim; ++
d)
4341 x_k += object->vertex(i) *
4342 GeometryInfo<structdim>::d_linear_shape_function(xi, i);
4347 for (
const unsigned int i :
4350 (x_k - trial_point) * object->vertex(i) *
4351 GeometryInfo<structdim>::d_linear_shape_function_gradient(xi,
4355 for (
const unsigned int i :
4357 for (const unsigned
int j :
4365 H_k += (
object->vertex(i) *
object->vertex(j)) * tmp;
4372 for (
const unsigned int i :
4374 x_k += object->vertex(i) *
4375 GeometryInfo<structdim>::d_linear_shape_function(xi, i);
4377 if (delta_xi.
norm() < 1e-7)
4393 template <
int structdim>
4400 static const std::size_t n_vertices_per_cell =
4402 n_independent_components;
4403 std::array<double, n_vertices_per_cell> copied_weights;
4404 for (
unsigned int i = 0; i < n_vertices_per_cell; ++i)
4406 copied_weights[i] = v[i];
4407 if (v[i] < 0.0 || v[i] > 1.0)
4412 std::sort(copied_weights.begin(), copied_weights.end());
4414 std::accumulate(copied_weights.begin(), copied_weights.end(), 0.0);
4419 template <
typename Iterator>
4422 const Iterator &
object,
4425 const int spacedim = Iterator::AccessorType::space_dimension;
4426 const int structdim = Iterator::AccessorType::structure_dimension;
4430 if (structdim >= spacedim)
4431 return projected_point;
4432 else if (structdim == 1 || structdim == 2)
4434 using namespace internal::ProjectToObject;
4439 const int dim = Iterator::AccessorType::dimension;
4442 &manifold) !=
nullptr)
4445 project_to_d_linear_object<Iterator, spacedim, structdim>(
4446 object, trial_point);
4491 const double step_size =
object->diameter() / 64.0;
4493 constexpr unsigned int n_vertices_per_cell =
4496 std::array<Point<spacedim>, n_vertices_per_cell>
vertices;
4497 for (
unsigned int vertex_n = 0; vertex_n < n_vertices_per_cell;
4499 vertices[vertex_n] = object->vertex(vertex_n);
4501 auto get_point_from_weights =
4504 return object->get_manifold().get_new_point(
4512 double guess_weights_sum = 0.0;
4513 for (
unsigned int vertex_n = 0; vertex_n < n_vertices_per_cell;
4516 const double distance =
4518 if (distance == 0.0)
4520 guess_weights = 0.0;
4521 guess_weights[vertex_n] = 1.0;
4522 guess_weights_sum = 1.0;
4527 guess_weights[vertex_n] = 1.0 / distance;
4528 guess_weights_sum += guess_weights[vertex_n];
4531 guess_weights /= guess_weights_sum;
4532 Assert(internal::weights_are_ok<structdim>(guess_weights),
4541 for (
unsigned int outer_n = 0; outer_n < 40; ++outer_n)
4543 const unsigned int dependent_direction =
4544 n_vertices_per_cell - 1;
4546 for (
unsigned int row_n = 0; row_n < n_vertices_per_cell;
4549 if (row_n != dependent_direction)
4551 current_gradient[row_n] =
4552 gradient_entry<spacedim, structdim>(
4554 dependent_direction,
4558 get_point_from_weights);
4560 current_gradient[dependent_direction] -=
4561 current_gradient[row_n];
4579 double gradient_weight = -0.5;
4580 auto gradient_weight_objective_function =
4581 [&](
const double gradient_weight_guess) ->
double {
4582 return (trial_point -
4583 get_point_from_weights(guess_weights +
4584 gradient_weight_guess *
4589 for (
unsigned int inner_n = 0; inner_n < 10; ++inner_n)
4591 const double update_numerator = centered_first_difference(
4594 gradient_weight_objective_function);
4595 const double update_denominator =
4596 centered_second_difference(
4599 gradient_weight_objective_function);
4603 if (
std::abs(update_denominator) == 0.0)
4606 gradient_weight - update_numerator / update_denominator;
4611 if (
std::abs(gradient_weight) > 10)
4613 gradient_weight = -10.0;
4623 guess_weights + gradient_weight * current_gradient;
4625 double new_gradient_weight = gradient_weight;
4626 for (
unsigned int iteration_count = 0; iteration_count < 40;
4629 if (internal::weights_are_ok<structdim>(tentative_weights))
4632 for (
unsigned int i = 0; i < n_vertices_per_cell; ++i)
4634 if (tentative_weights[i] < 0.0)
4636 tentative_weights -=
4637 (tentative_weights[i] / current_gradient[i]) *
4640 if (tentative_weights[i] < 0.0 ||
4641 1.0 < tentative_weights[i])
4643 new_gradient_weight /= 2.0;
4646 new_gradient_weight * current_gradient;
4653 if (!internal::weights_are_ok<structdim>(tentative_weights))
4658 if (get_point_from_weights(tentative_weights)
4659 .distance(trial_point) <
4660 get_point_from_weights(guess_weights).distance(trial_point))
4661 guess_weights = tentative_weights;
4664 Assert(internal::weights_are_ok<structdim>(guess_weights),
4667 Assert(internal::weights_are_ok<structdim>(guess_weights),
4669 projected_point = get_point_from_weights(guess_weights);
4679 for (
unsigned int line_n = 0;
4680 line_n < GeometryInfo<structdim>::lines_per_cell;
4683 line_projections[line_n] =
4686 std::sort(line_projections.begin(),
4687 line_projections.end(),
4689 return a.distance(trial_point) <
4690 b.distance(trial_point);
4692 if (line_projections[0].distance(trial_point) <
4693 projected_point.
distance(trial_point))
4694 projected_point = line_projections[0];
4700 return projected_point;
4703 return projected_point;
4710 template <
typename DataType,
4712 typename MeshCellIteratorType>
4714 inline void exchange_cell_data(
4715 const MeshType &mesh,
4716 const std::function<
4717 std_cxx17::optional<DataType>(
const MeshCellIteratorType &)> &pack,
4718 const std::function<
void(
const MeshCellIteratorType &,
const DataType &)>
4720 const std::function<
bool(
const MeshCellIteratorType &)> & cell_filter,
4721 const std::function<
void(
4722 const std::function<
void(
const MeshCellIteratorType &,
4724 const std::function<std::set<types::subdomain_id>(
4726 MeshType::space_dimension> &)>
4727 &compute_ghost_owners)
4729# ifndef DEAL_II_WITH_MPI
4734 (void)process_cells;
4735 (void)compute_ghost_owners;
4738 constexpr int dim = MeshType::dimension;
4739 constexpr int spacedim = MeshType::space_dimension;
4742 &mesh.get_triangulation());
4746 "The function exchange_cell_data_to_ghosts() only works with parallel triangulations."));
4748 if (
const auto tria =
dynamic_cast<
4750 &mesh.get_triangulation()))
4753 tria->with_artificial_cells(),
4755 "The functions GridTools::exchange_cell_data_to_ghosts() and "
4756 "GridTools::exchange_cell_data_to_level_ghosts() can only "
4757 "operate on a single layer of ghost cells. However, you have "
4758 "given a Triangulation object of type "
4759 "parallel::shared::Triangulation without artificial cells "
4760 "resulting in arbitrary numbers of ghost layers."));
4764 std::set<::types::subdomain_id> ghost_owners =
4765 compute_ghost_owners(*
tria);
4767 std::vector<typename CellId::binary_type>>
4770 for (
const auto ghost_owner : ghost_owners)
4771 neighbor_cell_list[ghost_owner] = {};
4773 process_cells([&](
const auto &cell,
const auto key) ->
void {
4774 if (cell_filter(cell))
4776 constexpr int spacedim = MeshType::space_dimension;
4777 neighbor_cell_list[key].emplace_back(
4778 cell->id().template to_binary<spacedim>());
4782 Assert(ghost_owners.size() == neighbor_cell_list.size(),
4794 const int mpi_tag_reply =
4798 std::vector<MPI_Request> requests(ghost_owners.size());
4800 unsigned int idx = 0;
4801 for (
const auto &it : neighbor_cell_list)
4804 const int ierr = MPI_Isend(it.second.data(),
4805 it.second.size() *
sizeof(it.second[0]),
4817 std::vector<MPI_Request> reply_requests(ghost_owners.size());
4818 std::vector<std::vector<char>> sendbuffers(ghost_owners.size());
4820 for (
unsigned int idx = 0; idx < ghost_owners.size(); ++idx)
4823 int ierr = MPI_Probe(MPI_ANY_SOURCE,
4830 ierr = MPI_Get_count(&status, MPI_BYTE, &len);
4837 std::vector<typename CellId::binary_type> cells_with_requests(
4839 std::vector<DataType> data_to_send;
4840 data_to_send.reserve(n_cells);
4841 std::vector<bool> cell_carries_data(n_cells,
false);
4843 ierr = MPI_Recv(cells_with_requests.data(),
4853 for (
unsigned int c = 0; c < static_cast<unsigned int>(n_cells); ++c)
4858 MeshCellIteratorType mesh_it(
tria,
4863 const std_cxx17::optional<DataType> data =
pack(mesh_it);
4866 data_to_send.emplace_back(*data);
4867 cell_carries_data[c] =
true;
4875 sendbuffers[idx].resize(
sizeof(std::size_t));
4880 std::size_t size_of_send =
4884 std::memcpy(sendbuffers[idx].data(),
4886 sizeof(std::size_t));
4890 if (data_to_send.size() < n_cells)
4896 ierr = MPI_Isend(sendbuffers[idx].data(),
4897 sendbuffers[idx].size(),
4902 &reply_requests[idx]);
4907 std::vector<char> receive;
4908 for (
unsigned int id = 0;
id < neighbor_cell_list.size(); ++id)
4911 int ierr = MPI_Probe(MPI_ANY_SOURCE,
4918 ierr = MPI_Get_count(&status, MPI_BYTE, &len);
4921 receive.resize(len);
4923 ierr = MPI_Recv(receive.data(),
4934 auto data_iterator = receive.begin();
4935 std::size_t size_of_received_data =
4936 Utilities::unpack<std::size_t>(data_iterator,
4937 data_iterator +
sizeof(std::size_t));
4938 data_iterator +=
sizeof(std::size_t);
4941 auto received_data = Utilities::unpack<std::vector<DataType>>(
4943 data_iterator + size_of_received_data,
4945 data_iterator += size_of_received_data;
4950 const std::vector<typename CellId::binary_type> &this_cell_list =
4951 neighbor_cell_list[status.MPI_SOURCE];
4953 std::vector<bool> cells_with_data;
4954 if (received_data.size() < this_cell_list.size())
4956 cells_with_data = Utilities::unpack<std::vector<bool>>(
4957 data_iterator, receive.end(),
false);
4963 auto received_data_iterator = received_data.begin();
4964 for (
unsigned int c = 0; c < this_cell_list.size(); ++c)
4965 if (cells_with_data.empty() || cells_with_data[c])
4970 MeshCellIteratorType cell(
tria,
4975 unpack(cell, *received_data_iterator);
4976 ++received_data_iterator;
4982 if (requests.size() > 0)
4985 MPI_Waitall(requests.size(), requests.data(), MPI_STATUSES_IGNORE);
4988 if (reply_requests.size() > 0)
4990 const int ierr = MPI_Waitall(reply_requests.size(),
4991 reply_requests.data(),
4992 MPI_STATUSES_IGNORE);
5002 template <
typename DataType,
typename MeshType>
5005 const MeshType & mesh,
5006 const std::function<std_cxx17::optional<DataType>(
5007 const typename MeshType::active_cell_iterator &)> &pack,
5008 const std::function<
void(
const typename MeshType::active_cell_iterator &,
5009 const DataType &)> & unpack,
5010 const std::function<
bool(
const typename MeshType::active_cell_iterator &)>
5013# ifndef DEAL_II_WITH_MPI
5020 internal::exchange_cell_data<DataType,
5022 typename MeshType::active_cell_iterator>(
5027 [&](
const auto &process) {
5028 for (
const auto &cell : mesh.active_cell_iterators())
5029 if (cell->is_ghost())
5032 [](
const auto &
tria) {
return tria.ghost_owners(); });
5038 template <
typename DataType,
typename MeshType>
5041 const MeshType & mesh,
5042 const std::function<std_cxx17::optional<DataType>(
5043 const typename MeshType::level_cell_iterator &)> &pack,
5044 const std::function<
void(
const typename MeshType::level_cell_iterator &,
5045 const DataType &)> & unpack,
5046 const std::function<
bool(
const typename MeshType::level_cell_iterator &)>
5049# ifndef DEAL_II_WITH_MPI
5056 internal::exchange_cell_data<DataType,
5058 typename MeshType::level_cell_iterator>(
5063 [&](
const auto &process) {
5064 for (
const auto &cell : mesh.cell_iterators())
5065 if (cell->is_ghost_on_level())
5066 process(cell, cell->level_subdomain_id());
5068 [](
const auto &
tria) {
return tria.level_ghost_owners(); });
ArrayView< typename std::remove_reference< typename std::iterator_traits< Iterator >::reference >::type, MemorySpaceType > make_array_view(const Iterator begin, const Iterator end)
std::array< unsigned int, 4 > binary_type
Abstract base class for mapping classes.
numbers::NumberTraits< Number >::real_type distance(const Point< dim, Number > &p) const
numbers::NumberTraits< Number >::real_type norm() const
virtual MPI_Comm get_communicator() const
cell_iterator create_cell_iterator(const CellId &cell_id) const
typename MeshType::active_cell_iterator type
#define DEAL_II_DEPRECATED
#define DEAL_II_NAMESPACE_OPEN
#define DEAL_II_CXX20_REQUIRES(condition)
#define DEAL_II_NAMESPACE_CLOSE
#define DeclException0(Exception0)
static ::ExceptionBase & ExcMeshNotOrientable()
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)
#define DeclExceptionMsg(Exception, defaulttext)
static ::ExceptionBase & ExcInternalError()
static ::ExceptionBase & ExcTriangulationHasBeenRefined()
static ::ExceptionBase & ExcDimensionMismatch(std::size_t arg1, std::size_t arg2)
#define DeclException1(Exception1, type1, outsequence)
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)
@ matrix
Contents is actually a matrix.
SymmetricTensor< 2, dim, Number > e(const Tensor< 2, dim, Number > &F)
SymmetricTensor< 2, dim, Number > d(const Tensor< 2, dim, Number > &F, const Tensor< 2, dim, Number > &dF_dt)
T sum(const T &t, const MPI_Comm mpi_communicator)
size_t pack(const T &object, std::vector< char > &dest_buffer, const bool allow_compression=true)
T unpack(const std::vector< char > &buffer, const bool allow_compression=true)
unsigned int n_cells(const internal::TriangulationImplementation::NumberCache< 1 > &c)
const types::manifold_id flat_manifold_id
::VectorizedArray< Number, width > abs(const ::VectorizedArray< Number, width > &)
unsigned int global_dof_index
unsigned int subdomain_id
const ::parallel::distributed::Triangulation< dim, spacedim > * triangulation
boost::geometry::index::rtree< LeafType, IndexType, IndexableGetter > RTree
DEAL_II_HOST constexpr SymmetricTensor< 2, dim, Number > invert(const SymmetricTensor< 2, dim, Number > &)
DEAL_II_HOST constexpr SymmetricTensor< 4, dim, Number > outer_product(const SymmetricTensor< 2, dim, Number > &t1, const SymmetricTensor< 2, dim, Number > &t2)
std::map< unsigned int, unsigned int > vertex_to_coinciding_vertex_group
std::map< unsigned int, std::vector< unsigned int > > coinciding_vertex_groups
const ::Triangulation< dim, spacedim > & tria