38#include <boost/container/small_vector.hpp>
51template <
int dim,
int spacedim>
55 , polynomial_degree(fe.tensor_degree())
56 , n_shape_functions(fe.n_dofs_per_cell())
61template <
int dim,
int spacedim>
81template <
int dim,
int spacedim>
86 const unsigned int n_original_q_points)
90 this->update_each = update_flags;
92 const unsigned int n_q_points = q.
size();
95 covariant.resize(n_original_q_points);
98 contravariant.resize(n_original_q_points);
101 volume_elements.resize(n_original_q_points);
106 shape_values.resize(n_shape_functions * n_q_points);
108 if (this->update_each &
116 shape_derivatives.resize(n_shape_functions * n_q_points);
118 if (this->update_each &
120 shape_second_derivatives.resize(n_shape_functions * n_q_points);
124 shape_third_derivatives.resize(n_shape_functions * n_q_points);
128 shape_fourth_derivatives.resize(n_shape_functions * n_q_points);
131 compute_shape_function_values(q.
get_points());
139template <
int dim,
int spacedim>
144 const unsigned int n_original_q_points)
146 initialize(update_flags, q, n_original_q_points);
148 if (this->update_each &
156 const auto reference_cell = this->
fe.reference_cell();
157 const auto n_faces = reference_cell.n_faces();
159 for (
unsigned int i = 0; i < n_faces; ++i)
161 unit_tangentials[i].resize(n_original_q_points);
162 std::fill(unit_tangentials[i].begin(),
163 unit_tangentials[i].end(),
164 reference_cell.template unit_tangential_vectors<dim>(i, 0));
167 unit_tangentials[n_faces + i].resize(n_original_q_points);
169 unit_tangentials[n_faces + i].begin(),
170 unit_tangentials[n_faces + i].end(),
171 reference_cell.template unit_tangential_vectors<dim>(i, 1));
179template <
int dim,
int spacedim>
188 const auto &tensor_pols = fe_poly->get_poly_space();
190 const unsigned int n_shape_functions =
fe.n_dofs_per_cell();
191 const unsigned int n_points = unit_points.size();
193 std::vector<double> values;
194 std::vector<Tensor<1, dim>> grads;
195 if (shape_values.size() != 0)
197 Assert(shape_values.size() == n_shape_functions * n_points,
199 values.resize(n_shape_functions);
201 if (shape_derivatives.size() != 0)
203 Assert(shape_derivatives.size() == n_shape_functions * n_points,
205 grads.resize(n_shape_functions);
208 std::vector<Tensor<2, dim>> grad2;
209 if (shape_second_derivatives.size() != 0)
211 Assert(shape_second_derivatives.size() == n_shape_functions * n_points,
213 grad2.resize(n_shape_functions);
216 std::vector<Tensor<3, dim>> grad3;
217 if (shape_third_derivatives.size() != 0)
219 Assert(shape_third_derivatives.size() == n_shape_functions * n_points,
221 grad3.resize(n_shape_functions);
224 std::vector<Tensor<4, dim>> grad4;
225 if (shape_fourth_derivatives.size() != 0)
227 Assert(shape_fourth_derivatives.size() == n_shape_functions * n_points,
229 grad4.resize(n_shape_functions);
233 if (shape_values.size() != 0 || shape_derivatives.size() != 0 ||
234 shape_second_derivatives.size() != 0 ||
235 shape_third_derivatives.size() != 0 ||
236 shape_fourth_derivatives.size() != 0)
237 for (
unsigned int point = 0; point < n_points; ++point)
239 tensor_pols.evaluate(
240 unit_points[point], values, grads, grad2, grad3, grad4);
242 if (shape_values.size() != 0)
243 for (
unsigned int i = 0; i < n_shape_functions; ++i)
244 shape(point, i) = values[i];
246 if (shape_derivatives.size() != 0)
247 for (
unsigned int i = 0; i < n_shape_functions; ++i)
248 derivative(point, i) = grads[i];
250 if (shape_second_derivatives.size() != 0)
251 for (
unsigned int i = 0; i < n_shape_functions; ++i)
252 second_derivative(point, i) = grad2[i];
254 if (shape_third_derivatives.size() != 0)
255 for (
unsigned int i = 0; i < n_shape_functions; ++i)
256 third_derivative(point, i) = grad3[i];
258 if (shape_fourth_derivatives.size() != 0)
259 for (
unsigned int i = 0; i < n_shape_functions; ++i)
260 fourth_derivative(point, i) = grad4[i];
267 namespace MappingFEImplementation
277 template <
int dim,
int spacedim>
279 maybe_compute_q_points(
281 const typename ::MappingFE<dim, spacedim>::InternalData &data,
283 const unsigned int n_q_points)
288 for (
unsigned int point = 0; point < n_q_points; ++point)
290 const double * shape = &data.shape(point + data_set, 0);
292 (shape[0] * data.mapping_support_points[0]);
293 for (
unsigned int k = 1; k < data.n_shape_functions; ++k)
294 for (
unsigned int i = 0; i < spacedim; ++i)
295 result[i] += shape[k] * data.mapping_support_points[k][i];
296 quadrature_points[point] = result;
310 template <
int dim,
int spacedim>
312 maybe_update_Jacobians(
314 const typename ::QProjector<dim>::DataSetDescriptor data_set,
315 const typename ::MappingFE<dim, spacedim>::InternalData &data,
316 const unsigned int n_q_points)
326 std::fill(data.contravariant.begin(),
327 data.contravariant.end(),
332 for (
unsigned int point = 0; point < n_q_points; ++point)
334 double result[spacedim][dim];
338 for (
unsigned int i = 0; i < spacedim; ++i)
339 for (
unsigned int j = 0; j < dim; ++j)
340 result[i][j] = data.derivative(point + data_set, 0)[j] *
341 data.mapping_support_points[0][i];
342 for (
unsigned int k = 1; k < data.n_shape_functions; ++k)
343 for (
unsigned int i = 0; i < spacedim; ++i)
344 for (
unsigned int j = 0; j < dim; ++j)
346 data.derivative(point + data_set, k)[j] *
347 data.mapping_support_points[k][i];
354 for (
unsigned int i = 0; i < spacedim; ++i)
355 for (
unsigned int j = 0; j < dim; ++j)
356 data.contravariant[point][i][j] = result[i][j];
363 for (
unsigned int point = 0; point < n_q_points; ++point)
365 data.covariant[point] =
366 (data.contravariant[point]).covariant_form();
373 for (
unsigned int point = 0; point < n_q_points; ++point)
374 data.volume_elements[point] =
375 data.contravariant[point].determinant();
385 template <
int dim,
int spacedim>
387 maybe_update_jacobian_grads(
390 const typename ::MappingFE<dim, spacedim>::InternalData &data,
392 const unsigned int n_q_points)
400 for (
unsigned int point = 0; point < n_q_points; ++point)
403 &data.second_derivative(point + data_set, 0);
404 double result[spacedim][dim][dim];
405 for (
unsigned int i = 0; i < spacedim; ++i)
406 for (
unsigned int j = 0; j < dim; ++j)
407 for (
unsigned int l = 0; l < dim; ++l)
409 (
second[0][j][l] * data.mapping_support_points[0][i]);
410 for (
unsigned int k = 1; k < data.n_shape_functions; ++k)
411 for (
unsigned int i = 0; i < spacedim; ++i)
412 for (
unsigned int j = 0; j < dim; ++j)
413 for (
unsigned int l = 0; l < dim; ++l)
416 data.mapping_support_points[k][i]);
418 for (
unsigned int i = 0; i < spacedim; ++i)
419 for (
unsigned int j = 0; j < dim; ++j)
420 for (
unsigned int l = 0; l < dim; ++l)
421 jacobian_grads[point][i][j][l] = result[i][j][l];
432 template <
int dim,
int spacedim>
434 maybe_update_jacobian_pushed_forward_grads(
437 const typename ::MappingFE<dim, spacedim>::InternalData &data,
439 const unsigned int n_q_points)
445 jacobian_pushed_forward_grads.size() + 1);
449 double tmp[spacedim][spacedim][spacedim];
450 for (
unsigned int point = 0; point < n_q_points; ++point)
453 &data.second_derivative(point + data_set, 0);
454 double result[spacedim][dim][dim];
455 for (
unsigned int i = 0; i < spacedim; ++i)
456 for (
unsigned int j = 0; j < dim; ++j)
457 for (
unsigned int l = 0; l < dim; ++l)
458 result[i][j][l] = (
second[0][j][l] *
459 data.mapping_support_points[0][i]);
460 for (
unsigned int k = 1; k < data.n_shape_functions; ++k)
461 for (
unsigned int i = 0; i < spacedim; ++i)
462 for (
unsigned int j = 0; j < dim; ++j)
463 for (
unsigned int l = 0; l < dim; ++l)
466 data.mapping_support_points[k][i]);
469 for (
unsigned int i = 0; i < spacedim; ++i)
470 for (
unsigned int j = 0; j < spacedim; ++j)
471 for (
unsigned int l = 0; l < dim; ++l)
474 result[i][0][l] * data.covariant[point][j][0];
475 for (
unsigned int jr = 1; jr < dim; ++jr)
477 tmp[i][j][l] += result[i][jr][l] *
478 data.covariant[point][j][jr];
483 for (
unsigned int i = 0; i < spacedim; ++i)
484 for (
unsigned int j = 0; j < spacedim; ++j)
485 for (
unsigned int l = 0; l < spacedim; ++l)
487 jacobian_pushed_forward_grads[point][i][j][l] =
488 tmp[i][j][0] * data.covariant[point][l][0];
489 for (
unsigned int lr = 1; lr < dim; ++lr)
491 jacobian_pushed_forward_grads[point][i][j][l] +=
492 tmp[i][j][lr] * data.covariant[point][l][lr];
506 template <
int dim,
int spacedim>
508 maybe_update_jacobian_2nd_derivatives(
511 const typename ::MappingFE<dim, spacedim>::InternalData &data,
513 const unsigned int n_q_points)
522 for (
unsigned int point = 0; point < n_q_points; ++point)
525 &data.third_derivative(point + data_set, 0);
526 double result[spacedim][dim][dim][dim];
527 for (
unsigned int i = 0; i < spacedim; ++i)
528 for (
unsigned int j = 0; j < dim; ++j)
529 for (
unsigned int l = 0; l < dim; ++l)
530 for (
unsigned int m = 0; m < dim; ++m)
533 data.mapping_support_points[0][i]);
534 for (
unsigned int k = 1; k < data.n_shape_functions; ++k)
535 for (
unsigned int i = 0; i < spacedim; ++i)
536 for (
unsigned int j = 0; j < dim; ++j)
537 for (
unsigned int l = 0; l < dim; ++l)
538 for (
unsigned int m = 0; m < dim; ++m)
539 result[i][j][l][m] +=
541 data.mapping_support_points[k][i]);
543 for (
unsigned int i = 0; i < spacedim; ++i)
544 for (
unsigned int j = 0; j < dim; ++j)
545 for (
unsigned int l = 0; l < dim; ++l)
546 for (
unsigned int m = 0; m < dim; ++m)
547 jacobian_2nd_derivatives[point][i][j][l][m] =
561 template <
int dim,
int spacedim>
563 maybe_update_jacobian_pushed_forward_2nd_derivatives(
566 const typename ::MappingFE<dim, spacedim>::InternalData &data,
568 & jacobian_pushed_forward_2nd_derivatives,
569 const unsigned int n_q_points)
575 jacobian_pushed_forward_2nd_derivatives.size() +
580 double tmp[spacedim][spacedim][spacedim][spacedim];
581 for (
unsigned int point = 0; point < n_q_points; ++point)
584 &data.third_derivative(point + data_set, 0);
585 double result[spacedim][dim][dim][dim];
586 for (
unsigned int i = 0; i < spacedim; ++i)
587 for (
unsigned int j = 0; j < dim; ++j)
588 for (
unsigned int l = 0; l < dim; ++l)
589 for (
unsigned int m = 0; m < dim; ++m)
592 data.mapping_support_points[0][i]);
593 for (
unsigned int k = 1; k < data.n_shape_functions; ++k)
594 for (
unsigned int i = 0; i < spacedim; ++i)
595 for (
unsigned int j = 0; j < dim; ++j)
596 for (
unsigned int l = 0; l < dim; ++l)
597 for (
unsigned int m = 0; m < dim; ++m)
598 result[i][j][l][m] +=
600 data.mapping_support_points[k][i]);
603 for (
unsigned int i = 0; i < spacedim; ++i)
604 for (
unsigned int j = 0; j < spacedim; ++j)
605 for (
unsigned int l = 0; l < dim; ++l)
606 for (
unsigned int m = 0; m < dim; ++m)
608 jacobian_pushed_forward_2nd_derivatives
609 [point][i][j][l][m] =
611 data.covariant[point][j][0];
612 for (
unsigned int jr = 1; jr < dim; ++jr)
613 jacobian_pushed_forward_2nd_derivatives[point]
616 result[i][jr][l][m] *
617 data.covariant[point][j][jr];
621 for (
unsigned int i = 0; i < spacedim; ++i)
622 for (
unsigned int j = 0; j < spacedim; ++j)
623 for (
unsigned int l = 0; l < spacedim; ++l)
624 for (
unsigned int m = 0; m < dim; ++m)
627 jacobian_pushed_forward_2nd_derivatives[point]
630 data.covariant[point][l][0];
631 for (
unsigned int lr = 1; lr < dim; ++lr)
633 jacobian_pushed_forward_2nd_derivatives
634 [point][i][j][lr][m] *
635 data.covariant[point][l][lr];
639 for (
unsigned int i = 0; i < spacedim; ++i)
640 for (
unsigned int j = 0; j < spacedim; ++j)
641 for (
unsigned int l = 0; l < spacedim; ++l)
642 for (
unsigned int m = 0; m < spacedim; ++m)
644 jacobian_pushed_forward_2nd_derivatives
645 [point][i][j][l][m] =
646 tmp[i][j][l][0] * data.covariant[point][m][0];
647 for (
unsigned int mr = 1; mr < dim; ++mr)
648 jacobian_pushed_forward_2nd_derivatives[point]
652 data.covariant[point][m][mr];
665 template <
int dim,
int spacedim>
667 maybe_update_jacobian_3rd_derivatives(
670 const typename ::MappingFE<dim, spacedim>::InternalData &data,
672 const unsigned int n_q_points)
681 for (
unsigned int point = 0; point < n_q_points; ++point)
684 &data.fourth_derivative(point + data_set, 0);
685 double result[spacedim][dim][dim][dim][dim];
686 for (
unsigned int i = 0; i < spacedim; ++i)
687 for (
unsigned int j = 0; j < dim; ++j)
688 for (
unsigned int l = 0; l < dim; ++l)
689 for (
unsigned int m = 0; m < dim; ++m)
690 for (
unsigned int n = 0; n < dim; ++n)
691 result[i][j][l][m][n] =
692 (fourth[0][j][l][m][n] *
693 data.mapping_support_points[0][i]);
694 for (
unsigned int k = 1; k < data.n_shape_functions; ++k)
695 for (
unsigned int i = 0; i < spacedim; ++i)
696 for (
unsigned int j = 0; j < dim; ++j)
697 for (
unsigned int l = 0; l < dim; ++l)
698 for (
unsigned int m = 0; m < dim; ++m)
699 for (
unsigned int n = 0; n < dim; ++n)
700 result[i][j][l][m][n] +=
701 (fourth[k][j][l][m][n] *
702 data.mapping_support_points[k][i]);
704 for (
unsigned int i = 0; i < spacedim; ++i)
705 for (
unsigned int j = 0; j < dim; ++j)
706 for (
unsigned int l = 0; l < dim; ++l)
707 for (
unsigned int m = 0; m < dim; ++m)
708 for (
unsigned int n = 0; n < dim; ++n)
709 jacobian_3rd_derivatives[point][i][j][l][m][n] =
710 result[i][j][l][m][n];
723 template <
int dim,
int spacedim>
725 maybe_update_jacobian_pushed_forward_3rd_derivatives(
728 const typename ::MappingFE<dim, spacedim>::InternalData &data,
730 & jacobian_pushed_forward_3rd_derivatives,
731 const unsigned int n_q_points)
737 jacobian_pushed_forward_3rd_derivatives.size() +
742 double tmp[spacedim][spacedim][spacedim][spacedim][spacedim];
743 for (
unsigned int point = 0; point < n_q_points; ++point)
746 &data.fourth_derivative(point + data_set, 0);
747 double result[spacedim][dim][dim][dim][dim];
748 for (
unsigned int i = 0; i < spacedim; ++i)
749 for (
unsigned int j = 0; j < dim; ++j)
750 for (
unsigned int l = 0; l < dim; ++l)
751 for (
unsigned int m = 0; m < dim; ++m)
752 for (
unsigned int n = 0; n < dim; ++n)
753 result[i][j][l][m][n] =
754 (fourth[0][j][l][m][n] *
755 data.mapping_support_points[0][i]);
756 for (
unsigned int k = 1; k < data.n_shape_functions; ++k)
757 for (
unsigned int i = 0; i < spacedim; ++i)
758 for (
unsigned int j = 0; j < dim; ++j)
759 for (
unsigned int l = 0; l < dim; ++l)
760 for (
unsigned int m = 0; m < dim; ++m)
761 for (
unsigned int n = 0; n < dim; ++n)
762 result[i][j][l][m][n] +=
763 (fourth[k][j][l][m][n] *
764 data.mapping_support_points[k][i]);
767 for (
unsigned int i = 0; i < spacedim; ++i)
768 for (
unsigned int j = 0; j < spacedim; ++j)
769 for (
unsigned int l = 0; l < dim; ++l)
770 for (
unsigned int m = 0; m < dim; ++m)
771 for (
unsigned int n = 0; n < dim; ++n)
774 result[i][0][l][m][n] *
775 data.covariant[point][j][0];
776 for (
unsigned int jr = 1; jr < dim; ++jr)
777 tmp[i][j][l][m][n] +=
778 result[i][jr][l][m][n] *
779 data.covariant[point][j][jr];
783 for (
unsigned int i = 0; i < spacedim; ++i)
784 for (
unsigned int j = 0; j < spacedim; ++j)
785 for (
unsigned int l = 0; l < spacedim; ++l)
786 for (
unsigned int m = 0; m < dim; ++m)
787 for (
unsigned int n = 0; n < dim; ++n)
789 jacobian_pushed_forward_3rd_derivatives
790 [point][i][j][l][m][n] =
792 data.covariant[point][l][0];
793 for (
unsigned int lr = 1; lr < dim; ++lr)
794 jacobian_pushed_forward_3rd_derivatives
795 [point][i][j][l][m][n] +=
796 tmp[i][j][lr][m][n] *
797 data.covariant[point][l][lr];
801 for (
unsigned int i = 0; i < spacedim; ++i)
802 for (
unsigned int j = 0; j < spacedim; ++j)
803 for (
unsigned int l = 0; l < spacedim; ++l)
804 for (
unsigned int m = 0; m < spacedim; ++m)
805 for (
unsigned int n = 0; n < dim; ++n)
808 jacobian_pushed_forward_3rd_derivatives
809 [point][i][j][l][0][n] *
810 data.covariant[point][m][0];
811 for (
unsigned int mr = 1; mr < dim; ++mr)
812 tmp[i][j][l][m][n] +=
813 jacobian_pushed_forward_3rd_derivatives
814 [point][i][j][l][mr][n] *
815 data.covariant[point][m][mr];
819 for (
unsigned int i = 0; i < spacedim; ++i)
820 for (
unsigned int j = 0; j < spacedim; ++j)
821 for (
unsigned int l = 0; l < spacedim; ++l)
822 for (
unsigned int m = 0; m < spacedim; ++m)
823 for (
unsigned int n = 0; n < spacedim; ++n)
825 jacobian_pushed_forward_3rd_derivatives
826 [point][i][j][l][m][n] =
828 data.covariant[point][n][0];
829 for (
unsigned int nr = 1; nr < dim; ++nr)
830 jacobian_pushed_forward_3rd_derivatives
831 [point][i][j][l][m][n] +=
832 tmp[i][j][l][m][nr] *
833 data.covariant[point][n][nr];
845template <
int dim,
int spacedim>
851 ExcMessage(
"It only makes sense to create polynomial mappings "
852 "with a polynomial degree greater or equal to one."));
857 const auto &mapping_support_points =
fe.get_unit_support_points();
859 const auto reference_cell =
fe.reference_cell();
861 const unsigned int n_points = mapping_support_points.size();
862 const unsigned int n_shape_functions = reference_cell.n_vertices();
867 for (
unsigned int point = 0; point < n_points; ++point)
868 for (
unsigned int i = 0; i < n_shape_functions; ++i)
870 reference_cell.d_linear_shape_function(mapping_support_points[point],
876template <
int dim,
int spacedim>
878 : fe(mapping.fe->clone())
879 , polynomial_degree(mapping.polynomial_degree)
880 , mapping_support_point_weights(mapping.mapping_support_point_weights)
885template <
int dim,
int spacedim>
886std::unique_ptr<Mapping<dim, spacedim>>
889 return std::make_unique<MappingFE<dim, spacedim>>(*this);
894template <
int dim,
int spacedim>
898 return polynomial_degree;
903template <
int dim,
int spacedim>
909 const std::vector<Point<spacedim>> support_points =
910 this->compute_mapping_support_points(cell);
914 for (
unsigned int i = 0; i < this->fe->n_dofs_per_cell(); ++i)
915 mapped_point += support_points[i] * this->fe->shape_value(i, p);
922template <
int dim,
int spacedim>
928 const std::vector<Point<spacedim>> support_points =
929 this->compute_mapping_support_points(cell);
931 const double eps = 1.e-12 * cell->diameter();
932 const unsigned int loop_limit = 10;
936 unsigned int loop = 0;
952 for (
unsigned int i = 0; i < this->fe->n_dofs_per_cell(); ++i)
954 mapped_point += support_points[i] * this->fe->shape_value(i, p_unit);
955 const auto grad_F_i = this->fe->shape_grad(i, p_unit);
956 const auto hessian_F_i = this->fe->shape_grad_grad(i, p_unit);
957 for (
unsigned int j = 0; j < dim; ++j)
959 grad_FT[j] += grad_F_i[j] * support_points[i];
960 for (
unsigned int l = 0; l < dim; ++l)
961 hess_FT[j][l] += hessian_F_i[j][l] * support_points[i];
966 const auto residual = p - mapped_point;
973 if (grad_FT_residual.norm() <= eps)
978 for (
unsigned int j = 0; j < dim; ++j)
979 for (
unsigned int l = 0; l < dim; ++l)
980 corrected_metric_tensor[j][l] =
981 -grad_FT[j] * grad_FT[l] + hess_FT[j][l] * residual;
984 const auto g_inverse =
invert(corrected_metric_tensor);
985 p_unit -=
Point<dim>(g_inverse * grad_FT_residual);
989 while (loop < loop_limit);
1003template <
int dim,
int spacedim>
1014 for (
unsigned int i = 0; i < 5; ++i)
1059template <
int dim,
int spacedim>
1060std::unique_ptr<typename Mapping<dim, spacedim>::InternalDataBase>
1064 std::unique_ptr<typename Mapping<dim, spacedim>::InternalDataBase> data_ptr =
1065 std::make_unique<InternalData>(*this->fe);
1067 data.
initialize(this->requires_update_flags(update_flags), q, q.
size());
1074template <
int dim,
int spacedim>
1075std::unique_ptr<typename Mapping<dim, spacedim>::InternalDataBase>
1080 std::unique_ptr<typename Mapping<dim, spacedim>::InternalDataBase> data_ptr =
1081 std::make_unique<InternalData>(*this->fe);
1085 this->fe->reference_cell(), quadrature),
1093template <
int dim,
int spacedim>
1094std::unique_ptr<typename Mapping<dim, spacedim>::InternalDataBase>
1099 std::unique_ptr<typename Mapping<dim, spacedim>::InternalDataBase> data_ptr =
1100 std::make_unique<InternalData>(*this->fe);
1104 this->fe->reference_cell(), quadrature),
1112template <
int dim,
int spacedim>
1127 const unsigned int n_q_points = quadrature.
size();
1149 internal::MappingFEImplementation::maybe_compute_q_points<dim, spacedim>(
1155 internal::MappingFEImplementation::maybe_update_Jacobians<dim, spacedim>(
1156 computed_cell_similarity,
1161 internal::MappingFEImplementation::maybe_update_jacobian_grads<dim, spacedim>(
1162 computed_cell_similarity,
1168 internal::MappingFEImplementation::maybe_update_jacobian_pushed_forward_grads<
1170 spacedim>(computed_cell_similarity,
1176 internal::MappingFEImplementation::maybe_update_jacobian_2nd_derivatives<
1178 spacedim>(computed_cell_similarity,
1184 internal::MappingFEImplementation::
1185 maybe_update_jacobian_pushed_forward_2nd_derivatives<dim, spacedim>(
1186 computed_cell_similarity,
1192 internal::MappingFEImplementation::maybe_update_jacobian_3rd_derivatives<
1194 spacedim>(computed_cell_similarity,
1200 internal::MappingFEImplementation::
1201 maybe_update_jacobian_pushed_forward_3rd_derivatives<dim, spacedim>(
1202 computed_cell_similarity,
1208 const UpdateFlags update_flags = data.update_each;
1209 const std::vector<double> &weights = quadrature.
get_weights();
1225 for (
unsigned int point = 0; point < n_q_points; ++point)
1227 if (dim == spacedim)
1237 1e-12 * Utilities::fixed_power<dim>(
1238 cell->diameter() /
std::sqrt(
double(dim))),
1240 cell->center(), det, point)));
1242 output_data.
JxW_values[point] = weights[point] * det;
1250 for (
unsigned int i = 0; i < spacedim; ++i)
1251 for (
unsigned int j = 0; j < dim; ++j)
1255 for (
unsigned int i = 0; i < dim; ++i)
1256 for (
unsigned int j = 0; j < dim; ++j)
1257 G[i][j] = DX_t[i] * DX_t[j];
1262 if (computed_cell_similarity ==
1273 Assert(spacedim == dim + 1,
1275 "There is no (unique) cell normal for " +
1277 "-dimensional cells in " +
1279 "-dimensional space. This only works if the "
1280 "space dimension is one greater than the "
1281 "dimensionality of the mesh cells."));
1293 if (cell->direction_flag() ==
false)
1308 for (
unsigned int point = 0; point < n_q_points; ++point)
1317 for (
unsigned int point = 0; point < n_q_points; ++point)
1322 return computed_cell_similarity;
1329 namespace MappingFEImplementation
1343 template <
int dim,
int spacedim>
1345 maybe_compute_face_data(
1346 const ::MappingFE<dim, spacedim> &mapping,
1347 const typename ::Triangulation<dim, spacedim>::cell_iterator
1349 const unsigned int face_no,
1350 const unsigned int subface_no,
1351 const unsigned int n_q_points,
1353 const typename ::MappingFE<dim, spacedim>::InternalData &data,
1357 const UpdateFlags update_flags = data.update_each;
1380 for (
unsigned int d = 0; d != dim - 1; ++d)
1382 Assert(face_no + cell->n_faces() * d <
1383 data.unit_tangentials.size(),
1386 data.aux[d].size() <=
1387 data.unit_tangentials[face_no + cell->n_faces() * d].size(),
1392 data.unit_tangentials[face_no + cell->n_faces() * d]),
1403 if (dim == spacedim)
1405 for (
unsigned int i = 0; i < n_q_points; ++i)
1415 (face_no == 0 ? -1 : +1);
1439 for (
unsigned int point = 0;
point < n_q_points; ++
point)
1445 data.contravariant[
point].transpose()[0];
1447 (face_no == 0 ? -1. : +1.) *
1458 cell_normal /= cell_normal.
norm();
1470 for (
unsigned int i = 0; i < n_q_points; ++i)
1474 data.quadrature_weights[i + data_set];
1479 const double area_ratio =
1481 cell->subface_case(face_no), subface_no);
1490 for (
unsigned int i = 0; i < n_q_points; ++i)
1496 for (
unsigned int point = 0;
point < n_q_points; ++
point)
1497 output_data.
jacobians[point] = data.contravariant[point];
1500 for (
unsigned int point = 0;
point < n_q_points; ++
point)
1502 data.covariant[point].transpose();
1513 template <
int dim,
int spacedim>
1516 const ::MappingFE<dim, spacedim> &mapping,
1517 const typename ::Triangulation<dim, spacedim>::cell_iterator
1519 const unsigned int face_no,
1520 const unsigned int subface_no,
1523 const typename ::MappingFE<dim, spacedim>::InternalData &data,
1527 const unsigned int n_q_points = quadrature.
size();
1529 maybe_compute_q_points<dim, spacedim>(data_set,
1542 maybe_update_jacobian_pushed_forward_grads<dim, spacedim>(
1548 maybe_update_jacobian_2nd_derivatives<dim, spacedim>(
1554 maybe_update_jacobian_pushed_forward_2nd_derivatives<dim, spacedim>(
1560 maybe_update_jacobian_3rd_derivatives<dim, spacedim>(
1566 maybe_update_jacobian_pushed_forward_3rd_derivatives<dim, spacedim>(
1588template <
int dim,
int spacedim>
1592 const unsigned int face_no,
1608 (&cell->get_triangulation() !=
1616 internal::MappingFEImplementation::do_fill_fe_face_values(
1623 cell->face_orientation(face_no),
1624 cell->face_flip(face_no),
1625 cell->face_rotation(face_no),
1627 quadrature[quadrature.
size() == 1 ? 0 : face_no],
1634template <
int dim,
int spacedim>
1638 const unsigned int face_no,
1639 const unsigned int subface_no,
1655 (&cell->get_triangulation() !=
1663 internal::MappingFEImplementation::do_fill_fe_face_values(
1671 cell->face_orientation(face_no),
1672 cell->face_flip(face_no),
1673 cell->face_rotation(face_no),
1675 cell->subface_case(face_no)),
1685 namespace MappingFEImplementation
1689 template <
int dim,
int spacedim,
int rank>
1706 const typename ::MappingFE<dim, spacedim>::InternalData *
>(
1707 &mapping_data) !=
nullptr),
1709 const typename ::MappingFE<dim, spacedim>::InternalData &data =
1711 const typename ::MappingFE<dim, spacedim>::InternalData &
>(
1714 switch (mapping_kind)
1721 "update_contravariant_transformation"));
1723 for (
unsigned int i = 0; i < input.size(); ++i)
1735 "update_contravariant_transformation"));
1739 "update_volume_elements"));
1744 for (
unsigned int i = 0; i < input.size(); ++i)
1748 output[i] /= data.volume_elements[i];
1760 "update_covariant_transformation"));
1762 for (
unsigned int i = 0; i < input.size(); ++i)
1774 template <
int dim,
int spacedim,
int rank>
1785 const typename ::MappingFE<dim, spacedim>::InternalData *
>(
1786 &mapping_data) !=
nullptr),
1788 const typename ::MappingFE<dim, spacedim>::InternalData &data =
1790 const typename ::MappingFE<dim, spacedim>::InternalData &
>(
1793 switch (mapping_kind)
1800 "update_covariant_transformation"));
1804 "update_contravariant_transformation"));
1807 for (
unsigned int i = 0; i < output.size(); ++i)
1824 "update_covariant_transformation"));
1827 for (
unsigned int i = 0; i < output.size(); ++i)
1844 "update_covariant_transformation"));
1848 "update_contravariant_transformation"));
1852 "update_volume_elements"));
1855 for (
unsigned int i = 0; i < output.size(); ++i)
1864 output[i] /= data.volume_elements[i];
1877 template <
int dim,
int spacedim>
1888 const typename ::MappingFE<dim, spacedim>::InternalData *
>(
1889 &mapping_data) !=
nullptr),
1891 const typename ::MappingFE<dim, spacedim>::InternalData &data =
1893 const typename ::MappingFE<dim, spacedim>::InternalData &
>(
1896 switch (mapping_kind)
1903 "update_covariant_transformation"));
1907 "update_contravariant_transformation"));
1909 for (
unsigned int q = 0; q < output.size(); ++q)
1910 for (
unsigned int i = 0; i < spacedim; ++i)
1912 double tmp1[dim][dim];
1913 for (
unsigned int J = 0; J < dim; ++J)
1914 for (
unsigned int K = 0; K < dim; ++K)
1917 data.contravariant[q][i][0] * input[q][0][J][K];
1918 for (
unsigned int I = 1; I < dim; ++I)
1920 data.contravariant[q][i][I] * input[q][I][J][K];
1922 for (
unsigned int j = 0; j < spacedim; ++j)
1925 for (
unsigned int K = 0; K < dim; ++K)
1927 tmp2[K] = data.covariant[q][j][0] * tmp1[0][K];
1928 for (
unsigned int J = 1; J < dim; ++J)
1929 tmp2[K] += data.covariant[q][j][J] * tmp1[J][K];
1931 for (
unsigned int k = 0; k < spacedim; ++k)
1933 output[q][i][j][k] =
1934 data.covariant[q][k][0] * tmp2[0];
1935 for (
unsigned int K = 1; K < dim; ++K)
1936 output[q][i][j][k] +=
1937 data.covariant[q][k][K] * tmp2[K];
1949 "update_covariant_transformation"));
1951 for (
unsigned int q = 0; q < output.size(); ++q)
1952 for (
unsigned int i = 0; i < spacedim; ++i)
1954 double tmp1[dim][dim];
1955 for (
unsigned int J = 0; J < dim; ++J)
1956 for (
unsigned int K = 0; K < dim; ++K)
1959 data.covariant[q][i][0] * input[q][0][J][K];
1960 for (
unsigned int I = 1; I < dim; ++I)
1962 data.covariant[q][i][I] * input[q][I][J][K];
1964 for (
unsigned int j = 0; j < spacedim; ++j)
1967 for (
unsigned int K = 0; K < dim; ++K)
1969 tmp2[K] = data.covariant[q][j][0] * tmp1[0][K];
1970 for (
unsigned int J = 1; J < dim; ++J)
1971 tmp2[K] += data.covariant[q][j][J] * tmp1[J][K];
1973 for (
unsigned int k = 0; k < spacedim; ++k)
1975 output[q][i][j][k] =
1976 data.covariant[q][k][0] * tmp2[0];
1977 for (
unsigned int K = 1; K < dim; ++K)
1978 output[q][i][j][k] +=
1979 data.covariant[q][k][K] * tmp2[K];
1992 "update_covariant_transformation"));
1996 "update_contravariant_transformation"));
2000 "update_volume_elements"));
2002 for (
unsigned int q = 0; q < output.size(); ++q)
2003 for (
unsigned int i = 0; i < spacedim; ++i)
2006 for (
unsigned int I = 0; I < dim; ++I)
2008 data.contravariant[q][i][I] / data.volume_elements[q];
2009 double tmp1[dim][dim];
2010 for (
unsigned int J = 0; J < dim; ++J)
2011 for (
unsigned int K = 0; K < dim; ++K)
2013 tmp1[J][K] = factor[0] * input[q][0][J][K];
2014 for (
unsigned int I = 1; I < dim; ++I)
2015 tmp1[J][K] += factor[I] * input[q][I][J][K];
2017 for (
unsigned int j = 0; j < spacedim; ++j)
2020 for (
unsigned int K = 0; K < dim; ++K)
2022 tmp2[K] = data.covariant[q][j][0] * tmp1[0][K];
2023 for (
unsigned int J = 1; J < dim; ++J)
2024 tmp2[K] += data.covariant[q][j][J] * tmp1[J][K];
2026 for (
unsigned int k = 0; k < spacedim; ++k)
2028 output[q][i][j][k] =
2029 data.covariant[q][k][0] * tmp2[0];
2030 for (
unsigned int K = 1; K < dim; ++K)
2031 output[q][i][j][k] +=
2032 data.covariant[q][k][K] * tmp2[K];
2047 template <
int dim,
int spacedim,
int rank>
2058 const typename ::MappingFE<dim, spacedim>::InternalData *
>(
2059 &mapping_data) !=
nullptr),
2061 const typename ::MappingFE<dim, spacedim>::InternalData &data =
2063 const typename ::MappingFE<dim, spacedim>::InternalData &
>(
2066 switch (mapping_kind)
2073 "update_covariant_transformation"));
2075 for (
unsigned int i = 0; i < output.size(); ++i)
2090template <
int dim,
int spacedim>
2098 internal::MappingFEImplementation::transform_fields(input,
2106template <
int dim,
int spacedim>
2114 internal::MappingFEImplementation::transform_differential_forms(input,
2122template <
int dim,
int spacedim>
2130 switch (mapping_kind)
2133 internal::MappingFEImplementation::transform_fields(input,
2142 internal::MappingFEImplementation::transform_gradients(input,
2154template <
int dim,
int spacedim>
2167 switch (mapping_kind)
2173 "update_covariant_transformation"));
2175 for (
unsigned int q = 0; q < output.size(); ++q)
2176 for (
unsigned int i = 0; i < spacedim; ++i)
2177 for (
unsigned int j = 0; j < spacedim; ++j)
2180 for (
unsigned int K = 0; K < dim; ++K)
2182 tmp[K] = data.
covariant[q][j][0] * input[q][i][0][K];
2183 for (
unsigned int J = 1; J < dim; ++J)
2184 tmp[K] += data.
covariant[q][j][J] * input[q][i][J][K];
2186 for (
unsigned int k = 0; k < spacedim; ++k)
2188 output[q][i][j][k] = data.
covariant[q][k][0] * tmp[0];
2189 for (
unsigned int K = 1; K < dim; ++K)
2190 output[q][i][j][k] += data.
covariant[q][k][K] * tmp[K];
2203template <
int dim,
int spacedim>
2211 switch (mapping_kind)
2216 internal::MappingFEImplementation::transform_hessians(input,
2230 template <
int spacedim>
2232 check_all_manifold_ids_identical(
2240 template <
int spacedim>
2242 check_all_manifold_ids_identical(
2245 const auto m_id = cell->manifold_id();
2247 for (
const auto f : cell->face_indices())
2248 if (m_id != cell->face(f)->manifold_id())
2256 template <
int spacedim>
2258 check_all_manifold_ids_identical(
2261 const auto m_id = cell->manifold_id();
2263 for (
const auto f : cell->face_indices())
2264 if (m_id != cell->face(f)->manifold_id())
2267 for (
const auto l : cell->line_indices())
2268 if (m_id != cell->line(l)->manifold_id())
2277template <
int dim,
int spacedim>
2278std::vector<Point<spacedim>>
2283 check_all_manifold_ids_identical(cell),
2285 "All entities of a cell need to have the same manifold id as the cell has."));
2287 std::vector<Point<spacedim>>
vertices(cell->n_vertices());
2289 for (
const unsigned int i : cell->vertex_indices())
2292 std::vector<Point<spacedim>> mapping_support_points(
2293 fe->get_unit_support_points().size());
2295 cell->get_manifold().get_new_points(
vertices,
2296 mapping_support_point_weights,
2297 mapping_support_points);
2299 return mapping_support_points;
2304template <
int dim,
int spacedim>
2314template <
int dim,
int spacedim>
2319 Assert(dim == reference_cell.get_dimension(),
2320 ExcMessage(
"The dimension of your mapping (" +
2322 ") and the reference cell cell_type (" +
2324 " ) do not agree."));
2326 return fe->reference_cell() == reference_cell;
2332#include "mapping_fe.inst"
ArrayView< typename std::remove_reference< typename std::iterator_traits< Iterator >::reference >::type, MemorySpaceType > make_array_view(const Iterator begin, const Iterator end)
void initialize_face(const UpdateFlags update_flags, const Quadrature< dim > &quadrature, const unsigned int n_original_q_points)
std::vector< Point< spacedim > > mapping_support_points
void initialize(const UpdateFlags update_flags, const Quadrature< dim > &quadrature, const unsigned int n_original_q_points)
Triangulation< dim, spacedim >::cell_iterator cell_of_current_support_points
void compute_shape_function_values(const std::vector< Point< dim > > &unit_points)
std::vector< DerivativeForm< 1, dim, spacedim > > contravariant
std::vector< DerivativeForm< 1, dim, spacedim > > covariant
virtual std::size_t memory_consumption() const override
InternalData(const FiniteElement< dim, spacedim > &fe)
virtual void fill_fe_subface_values(const typename Triangulation< dim, spacedim >::cell_iterator &cell, const unsigned int face_no, const unsigned int subface_no, const Quadrature< dim - 1 > &quadrature, const typename Mapping< dim, spacedim >::InternalDataBase &internal_data, ::internal::FEValuesImplementation::MappingRelatedData< dim, spacedim > &output_data) const override
const unsigned int polynomial_degree
virtual void fill_fe_face_values(const typename Triangulation< dim, spacedim >::cell_iterator &cell, const unsigned int face_no, const hp::QCollection< dim - 1 > &quadrature, const typename Mapping< dim, spacedim >::InternalDataBase &internal_data, ::internal::FEValuesImplementation::MappingRelatedData< dim, spacedim > &output_data) const override
MappingFE(const FiniteElement< dim, spacedim > &fe)
virtual std::unique_ptr< typename Mapping< dim, spacedim >::InternalDataBase > get_face_data(const UpdateFlags flags, const hp::QCollection< dim - 1 > &quadrature) const override
virtual Point< dim > transform_real_to_unit_cell(const typename Triangulation< dim, spacedim >::cell_iterator &cell, const Point< spacedim > &p) const override
virtual UpdateFlags requires_update_flags(const UpdateFlags update_flags) const override
Table< 2, double > mapping_support_point_weights
virtual std::vector< Point< spacedim > > compute_mapping_support_points(const typename Triangulation< dim, spacedim >::cell_iterator &cell) const
virtual void transform(const ArrayView< const Tensor< 1, dim > > &input, const MappingKind kind, const typename Mapping< dim, spacedim >::InternalDataBase &internal, const ArrayView< Tensor< 1, spacedim > > &output) const override
virtual CellSimilarity::Similarity fill_fe_values(const typename Triangulation< dim, spacedim >::cell_iterator &cell, const CellSimilarity::Similarity cell_similarity, const Quadrature< dim > &quadrature, const typename Mapping< dim, spacedim >::InternalDataBase &internal_data, ::internal::FEValuesImplementation::MappingRelatedData< dim, spacedim > &output_data) const override
virtual BoundingBox< spacedim > get_bounding_box(const typename Triangulation< dim, spacedim >::cell_iterator &cell) const override
virtual std::unique_ptr< typename Mapping< dim, spacedim >::InternalDataBase > get_data(const UpdateFlags, const Quadrature< dim > &quadrature) const override
virtual std::unique_ptr< typename Mapping< dim, spacedim >::InternalDataBase > get_subface_data(const UpdateFlags flags, const Quadrature< dim - 1 > &quadrature) const override
unsigned int get_degree() const
virtual bool is_compatible_with(const ReferenceCell &reference_cell) const override
virtual std::unique_ptr< Mapping< dim, spacedim > > clone() const override
virtual Point< spacedim > transform_unit_to_real_cell(const typename Triangulation< dim, spacedim >::cell_iterator &cell, const Point< dim > &p) const override
const std::unique_ptr< FiniteElement< dim, spacedim > > fe
Abstract base class for mapping classes.
static DataSetDescriptor cell()
const std::vector< double > & get_weights() const
const std::vector< Point< dim > > & get_points() const
unsigned int size() const
numbers::NumberTraits< Number >::real_type norm() const
Triangulation< dim, spacedim > & get_triangulation()
unsigned int size() const
unsigned int max_n_quadrature_points() const
#define DEAL_II_NAMESPACE_OPEN
#define DEAL_II_DISABLE_EXTRA_DIAGNOSTICS
#define DEAL_II_NAMESPACE_CLOSE
#define DEAL_II_ENABLE_EXTRA_DIAGNOSTICS
@ update_jacobian_pushed_forward_2nd_derivatives
@ update_volume_elements
Determinant of the Jacobian.
@ update_contravariant_transformation
Contravariant transformation.
@ update_jacobian_pushed_forward_grads
@ update_jacobian_3rd_derivatives
@ update_jacobian_grads
Gradient of volume element.
@ update_normal_vectors
Normal vectors.
@ update_JxW_values
Transformed quadrature weights.
@ update_covariant_transformation
Covariant transformation.
@ update_jacobians
Volume element.
@ update_inverse_jacobians
Volume element.
@ update_quadrature_points
Transformed quadrature points.
@ update_jacobian_pushed_forward_3rd_derivatives
@ update_boundary_forms
Outer normal vector, not normalized.
@ update_jacobian_2nd_derivatives
static ::ExceptionBase & ExcNotImplemented()
#define Assert(cond, exc)
#define AssertDimension(dim1, dim2)
#define AssertIndexRange(index, range)
static ::ExceptionBase & ExcInternalError()
static ::ExceptionBase & ExcDimensionMismatch(std::size_t arg1, std::size_t arg2)
static ::ExceptionBase & ExcMessage(std::string arg1)
#define AssertThrow(cond, exc)
@ mapping_covariant_gradient
@ mapping_contravariant_hessian
@ mapping_covariant_hessian
@ mapping_contravariant_gradient
std::enable_if< std::is_fundamental< T >::value, std::size_t >::type memory_consumption(const T &t)
Point< spacedim > point(const gp_Pnt &p, const double tolerance=1e-10)
std::string to_string(const number value, const unsigned int digits=numbers::invalid_unsigned_int)
std::string int_to_string(const unsigned int value, const unsigned int digits=numbers::invalid_unsigned_int)
void transform_differential_forms(const ArrayView< const DerivativeForm< rank, dim, spacedim > > &input, const MappingKind mapping_kind, const typename Mapping< dim, spacedim >::InternalDataBase &mapping_data, const ArrayView< Tensor< rank+1, spacedim > > &output)
void transform_gradients(const ArrayView< const Tensor< rank, dim > > &input, const MappingKind mapping_kind, const typename Mapping< dim, spacedim >::InternalDataBase &mapping_data, const ArrayView< Tensor< rank, spacedim > > &output)
void transform_hessians(const ArrayView< const Tensor< 3, dim > > &input, const MappingKind mapping_kind, const typename Mapping< dim, spacedim >::InternalDataBase &mapping_data, const ArrayView< Tensor< 3, spacedim > > &output)
void do_fill_fe_face_values(const ::MappingQ< dim, spacedim > &mapping, const typename ::Triangulation< dim, spacedim >::cell_iterator &cell, const unsigned int face_no, const unsigned int subface_no, const typename QProjector< dim >::DataSetDescriptor data_set, const Quadrature< dim - 1 > &quadrature, const typename ::MappingQ< dim, spacedim >::InternalData &data, internal::FEValuesImplementation::MappingRelatedData< dim, spacedim > &output_data)
void maybe_compute_face_data(const ::MappingQ< dim, spacedim > &mapping, const typename ::Triangulation< dim, spacedim >::cell_iterator &cell, const unsigned int face_no, const unsigned int subface_no, const unsigned int n_q_points, const std::vector< double > &weights, const typename ::MappingQ< dim, spacedim >::InternalData &data, internal::FEValuesImplementation::MappingRelatedData< dim, spacedim > &output_data)
static const unsigned int invalid_unsigned_int
::VectorizedArray< Number, width > sqrt(const ::VectorizedArray< Number, width > &)
static double subface_ratio(const internal::SubfaceCase< dim > &subface_case, const unsigned int subface_no)
constexpr Number determinant(const SymmetricTensor< 2, dim, Number > &)
constexpr SymmetricTensor< 2, dim, Number > invert(const SymmetricTensor< 2, dim, Number > &)
constexpr Tensor< 1, dim, Number > cross_product_2d(const Tensor< 1, dim, Number > &src)
constexpr Tensor< 1, dim, typename ProductType< Number1, Number2 >::type > cross_product_3d(const Tensor< 1, dim, Number1 > &src1, const Tensor< 1, dim, Number2 > &src2)