1 #pragma once // Ensure that file is included only once in a single compilation.
23 template <
typename quadrature_t,
typename shape_t,
typename return_t =
double>
34 static constexpr
unsigned int dim() {
return shape_t::dim(); }
40 return Hypercube<
dim()>::pow(quadrature_t::n_quad_points());
46 static constexpr std::array<return_t, quadrature_t::n_points()>
quad_points =
47 quadrature_t::template points<return_t>();
51 static constexpr std::array<return_t, quadrature_t::n_points()>
quad_weights =
52 quadrature_t::template weights<return_t>();
58 static constexpr
unsigned int n_fun_1D = shape_t::shape_fun_t::shape_fun_1d::n_fun();
62 static constexpr std::array<std::array<return_t, quadrature_t::n_points()>,
n_fun_1D>
65 std::array<std::array<return_t, quadrature_t::n_points()>,
n_fun_1D> result;
67 for (
unsigned int fct = 0; fct <
n_fun_1D; ++fct)
68 for (
unsigned int pt = 0; pt < quadrature_t::n_points(); ++pt)
69 result[fct][pt] = shape_t::shape_fun_t::shape_fun_1d::template fct_val<return_t>(
70 fct, quadrature_t::points()[pt]);
77 std::array<std::array<return_t, quadrature_t::n_points()>,
80 std::array<std::array<return_t, quadrature_t::n_points()>,
n_fun_1D> result;
82 for (
unsigned int fct = 0; fct <
n_fun_1D; ++fct)
83 for (
unsigned int pt = 0; pt < quadrature_t::n_points(); ++pt)
84 result[fct][pt] = shape_t::shape_fun_t::shape_fun_1d::template der_val<return_t>(
85 fct, quadrature_t::points()[pt]);
94 std::array<std::array<return_t, 2>,
n_fun_1D> result;
96 for (
unsigned int fct = 0; fct <
n_fun_1D; ++fct)
97 for (
unsigned int pt = 0; pt < 2; ++pt)
98 result[fct][pt] = shape_t::shape_fun_t::shape_fun_1d::template fct_val<return_t>(fct, pt);
107 std::array<std::array<return_t, 2>,
n_fun_1D> result;
109 for (
unsigned int fct = 0; fct <
n_fun_1D; ++fct)
110 for (
unsigned int pt = 0; pt < 2; ++pt)
111 result[fct][pt] = shape_t::shape_fun_t::shape_fun_1d::template der_val<return_t>(fct, pt);
120 static constexpr std::array<std::array<return_t, quadrature_t::n_points()>,
n_fun_1D>
125 static constexpr std::array<std::array<return_t, quadrature_t::n_points()>,
n_fun_1D>
147 "Indices of shape functions must be smaller than amount of shape functions.");
148 return_t result = 0.;
165 "Indices of shape functions must be smaller than amount of shape functions.");
166 return_t result = 0.;
183 "Indices of shape functions must be smaller than amount of shape functions.");
184 return_t result = 0.;
201 "Indices of shape functions must be smaller than amount of shape functions.");
202 return_t result = 0.;
218 return_t integral = 1.;
221 for (
unsigned int dim_fct = 0; dim_fct <
dim(); ++dim_fct)
234 const unsigned int j,
235 const unsigned int dim_der)
237 return_t integral = 1.;
240 for (
unsigned int dim_fct = 0; dim_fct <
dim(); ++dim_fct)
241 if (dim_der == dim_fct)
256 const unsigned int j,
257 const unsigned int dim_der)
259 return_t integral = 1.;
262 for (
unsigned int dim_fct = 0; dim_fct <
dim(); ++dim_fct)
263 if (dim_der == dim_fct)
278 const unsigned int j,
279 const unsigned int bdr)
281 return_t integral = 1.;
284 unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
285 for (
unsigned int dim_fct = 0; dim_fct <
dim(); ++dim_fct)
286 if (bdr_dim == dim_fct)
303 const unsigned int j,
304 const unsigned int bdr)
306 return_t integral = 1.;
308 std::array<
unsigned int, std::max(
dim() - 1, 1U)> dec_j =
310 unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
311 for (
unsigned int dim_fct = 0; dim_fct <
dim(); ++dim_fct)
312 if (bdr_dim == dim_fct)
332 template <
typename point_t,
334 return_t fun(
const point_t&,
const return_t),
335 typename smallVec_t = point_t>
337 const unsigned int j,
339 const return_t f_param = 0.)
341 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
342 return_t integral = 0., quad_val;
345 std::array<
unsigned int,
dim()> dec_q;
348 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim()); ++q)
350 dec_q =
Hypercube<
dim()>::index_decompose(q, quadrature_t::n_points());
352 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
358 integral += fun(geom.map_ref_to_phys(quad_pt), f_param) * quad_val;
360 return integral * geom.area();
377 template <
typename point_t,
379 point_t fun(
const point_t&,
const return_t),
380 typename smallVec_t = point_t>
382 const unsigned int j,
383 const unsigned int dimension,
385 const return_t f_param = 0.)
387 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
388 return_t integral = 0., quad_val;
391 std::array<
unsigned int,
dim()> dec_q;
393 const auto mat_q = geom.mat_q();
395 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim()); ++q)
397 dec_q =
Hypercube<
dim()>::index_decompose(q, quadrature_t::n_points());
399 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
406 scalar_product(fun(geom.map_ref_to_phys(quad_pt), f_param), mat_q.get_column(dimension)) *
409 return integral * geom.area();
420 template <
typename geom_t>
423 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
424 return_t integral = 1.;
427 for (
unsigned int dim_fct = 0; dim_fct <
dim(); ++dim_fct)
429 return integral * geom.area();
442 template <
typename geom_t, std::
size_t array_size,
typename floating_t>
444 const std::array<floating_t, array_size>& js,
447 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
448 return_t integral = 0., quad_val, is_val, js_val, val_helper;
450 std::array<
unsigned int,
dim()> dec_k, dec_q;
452 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim()); ++q)
454 dec_q =
Hypercube<
dim()>::index_decompose(q, quadrature_t::n_points());
459 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
462 for (
unsigned int k = 0; k < array_size; ++k)
466 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
468 is_val += is[k] * val_helper;
469 js_val += js[k] * val_helper;
471 integral += quad_val * is_val * js_val;
473 return integral * geom.area();
487 template <
typename point_t,
489 return_t fun(
const point_t&,
const return_t),
490 typename smallVec_t = point_t>
493 const return_t f_param = 0.)
495 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
496 return_t integral = 0., quad_val;
498 std::array<
unsigned int,
dim()> dec_q;
501 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim()); ++q)
503 dec_q =
Hypercube<
dim()>::index_decompose(q, quadrature_t::n_points());
505 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
510 integral += fun(geom.map_ref_to_phys(quad_pt), f_param) * quad_val;
512 return integral * geom.area();
526 template <
typename point_t,
528 return_t fun(
const point_t&,
const return_t),
529 typename smallVec_t = point_t>
532 const return_t f_param = 0.)
534 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
535 return_t integral = 0., quad_val;
537 std::array<
unsigned int,
dim()> dec_q;
540 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim()); ++q)
542 dec_q =
Hypercube<
dim()>::index_decompose(q, quadrature_t::n_points());
544 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
549 integral += fun(geom.map_ref_to_phys(quad_pt), f_param) * quad_val;
568 template <
typename smallVec_t,
570 unsigned int poly_deg_i = shape_t::degree(),
571 unsigned int poly_deg_j = shape_t::degree()>
573 const unsigned int j,
576 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
577 static_assert(poly_deg_i <= shape_t::degree() && poly_deg_j <= shape_t::degree(),
578 "The maximum polynomial degrees must be larger than or equal to the given ones.");
579 smallVec_t integral(1.);
580 std::array<
unsigned int,
dim()> dec_i =
Hypercube<
dim()>::index_decompose(i, poly_deg_i + 1);
581 std::array<
unsigned int,
dim()> dec_j =
Hypercube<
dim()>::index_decompose(j, poly_deg_j + 1);
582 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
583 for (
unsigned int dim_fct = 0; dim_fct < geom_t::hyEdge_dim(); ++dim_fct)
588 return geom.area() * integral /
transposed(geom.mat_r());
603 template <
typename point_t,
605 return_t fun(
const point_t&,
const return_t),
606 typename smallVec_t = point_t>
608 const unsigned int j,
610 return_t f_param = 0.)
612 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
613 return_t integral = 0., quad_weight;
616 std::array<
unsigned int,
dim()> dec_q;
617 smallVec_t quad_pt, nabla_phi_i, nabla_phi_j;
620 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim()); ++q)
622 dec_q =
Hypercube<
dim()>::index_decompose(q, quadrature_t::n_points());
626 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
630 for (
unsigned int dim_fct = 0; dim_fct < geom_t::hyEdge_dim(); ++dim_fct)
644 integral += quad_weight * fun(geom.map_ref_to_phys(quad_pt), f_param) *
647 return geom.area() * integral;
662 template <
typename point_t,
664 return_t fun(
const point_t&,
const return_t),
665 typename smallVec_t = point_t>
667 const unsigned int dim_der,
669 return_t f_param = 0.)
671 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
672 return_t integral = 0., quad_weight;
674 std::array<
unsigned int,
dim()> dec_q;
675 smallVec_t quad_pt, nabla_phi_i;
678 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim()); ++q)
680 dec_q =
Hypercube<
dim()>::index_decompose(q, quadrature_t::n_points());
683 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
687 for (
unsigned int dim_fct = 0; dim_fct < geom_t::hyEdge_dim(); ++dim_fct)
696 quad_weight * fun(geom.map_ref_to_phys(quad_pt), f_param) * (nabla_phi_i / rT)[dim_der];
698 return geom.area() * integral;
715 template <
typename point_t,
717 point_t fun(
const point_t&,
const return_t),
718 typename smallVec_t = point_t>
720 const unsigned int j,
722 const return_t f_param = 0.)
724 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
725 return_t integral = 0., quad_val;
728 std::array<
unsigned int,
dim()> dec_q;
729 smallVec_t quad_pt, nabla_phi_i;
734 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim()); ++q)
736 dec_q =
Hypercube<
dim()>::index_decompose(q, quadrature_t::n_points());
739 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
743 for (
unsigned int dim_fct = 0; dim_fct < geom_t::hyEdge_dim(); ++dim_fct)
751 nabla_phi_i = nabla_phi_i / rT;
752 fun_val = qT * fun(geom.map_ref_to_phys(quad_pt), f_param);
753 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
754 integral += fun_val[
dim] * nabla_phi_i[
dim] * quad_val;
756 return integral * geom.area();
772 template <
typename point_t,
774 point_t fun(
const point_t&,
const return_t),
775 typename smallVec_t = point_t>
777 const unsigned int j,
778 const unsigned int bdr,
780 return_t f_param = 0.)
782 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
783 return_t integral = 0., quad_weight, phi_i, phi_j, winding;
786 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
788 point_t normal = geom.inner_normal(bdr);
789 const unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
791 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
793 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
797 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
801 quad_pt[
dim] = (return_t)bdr_ind;
813 winding =
scalar_product(normal, fun(geom.map_ref_to_phys(quad_pt), f_param));
815 integral += geom.face_area(bdr) * quad_weight * phi_i * phi_j * winding;
835 template <
typename point_t,
837 point_t fun(
const point_t&,
const return_t),
838 typename smallVec_t = point_t>
840 const unsigned int j,
841 const unsigned int bdr,
843 return_t f_param = 0.)
845 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
846 return_t integral = 0., quad_weight, phi_i, phi_j, winding;
849 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
851 point_t normal = geom.inner_normal(bdr);
852 const unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
854 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
856 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
860 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
864 quad_pt[
dim] = (return_t)bdr_ind;
876 winding =
scalar_product(normal, fun(geom.map_ref_to_phys(quad_pt), f_param));
878 integral += geom.face_area(bdr) * quad_weight * phi_i * phi_j;
898 template <
typename point_t,
900 point_t fun(
const point_t&,
const return_t),
901 typename smallVec_t = point_t>
903 const unsigned int j,
904 const unsigned int bdr,
906 return_t f_param = 0.)
908 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
909 return_t integral = 0., quad_weight, phi_i, psi_j, winding;
911 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_j =
913 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
915 point_t normal = geom.inner_normal(bdr);
916 const unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
918 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
920 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
924 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
928 quad_pt[
dim] = (return_t)bdr_ind;
939 winding =
scalar_product(normal, fun(geom.map_ref_to_phys(quad_pt), f_param));
942 integral += geom.face_area(bdr) * quad_weight * phi_i * psi_j * winding;
962 template <
typename point_t,
964 point_t fun(
const point_t&,
const return_t),
965 typename smallVec_t = point_t>
967 const unsigned int j,
968 const unsigned int bdr,
970 return_t f_param = 0.)
972 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
973 return_t integral = 0., quad_weight, phi_i, psi_j, winding;
975 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_j =
977 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
979 point_t normal = geom.inner_normal(bdr);
980 const unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
982 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
984 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
988 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
992 quad_pt[
dim] = (return_t)bdr_ind;
1003 winding =
scalar_product(normal, fun(geom.map_ref_to_phys(quad_pt), f_param));
1006 integral += geom.face_area(bdr) * quad_weight * phi_i * psi_j;
1026 template <
typename point_t,
1028 point_t fun(
const point_t&,
const return_t),
1029 typename smallVec_t = point_t>
1031 const unsigned int j,
1032 const unsigned int bdr,
1034 return_t f_param = 0.)
1036 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1037 return_t integral = 0., quad_weight, psi_i, phi_j, winding;
1038 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_i =
1041 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
1043 point_t normal = geom.inner_normal(bdr);
1044 const unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
1046 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
1048 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
1052 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
1056 quad_pt[
dim] = (return_t)bdr_ind;
1067 winding =
scalar_product(normal, fun(geom.map_ref_to_phys(quad_pt), f_param));
1069 integral += geom.face_area(bdr) * quad_weight * psi_i * phi_j * winding;
1088 template <
typename point_t,
1090 point_t fun(
const point_t&,
const return_t),
1091 typename smallVec_t = point_t>
1093 const unsigned int j,
1094 const unsigned int bdr,
1096 return_t f_param = 0.)
1098 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1099 return_t integral = 0., quad_weight, psi_i, phi_j, winding;
1100 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_i =
1103 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
1105 point_t normal = geom.inner_normal(bdr);
1106 const unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
1108 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
1110 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
1114 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
1118 quad_pt[
dim] = (return_t)bdr_ind;
1129 winding =
scalar_product(normal, fun(geom.map_ref_to_phys(quad_pt), f_param));
1131 integral += geom.face_area(bdr) * quad_weight * psi_i * phi_j;
1150 template <
typename point_t,
1152 point_t fun(
const point_t&,
const return_t),
1153 typename smallVec_t = point_t>
1155 const unsigned int j,
1156 const unsigned int bdr,
1158 return_t f_param = 0.)
1160 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1161 return_t integral = 0., quad_weight, psi_i, psi_j, winding;
1162 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_i =
1164 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_j =
1166 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
1168 point_t normal = geom.inner_normal(bdr);
1169 unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
1171 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
1173 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
1177 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
1181 quad_pt[
dim] = (return_t)bdr_ind;
1191 winding =
scalar_product(normal, fun(geom.map_ref_to_phys(quad_pt), f_param));
1193 integral += geom.face_area(bdr) * quad_weight * psi_i * psi_j * winding;
1211 template <
typename point_t,
1213 point_t fun(
const point_t&,
const return_t),
1214 typename smallVec_t = point_t>
1216 const unsigned int j,
1217 const unsigned int bdr,
1219 return_t f_param = 0.)
1221 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1222 return_t integral = 0., quad_weight, psi_i, psi_j, winding;
1223 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_i =
1225 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_j =
1227 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
1229 point_t normal = geom.inner_normal(bdr);
1230 unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
1232 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
1234 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
1238 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
1242 quad_pt[
dim] = (return_t)bdr_ind;
1252 winding =
scalar_product(normal, fun(geom.map_ref_to_phys(quad_pt), f_param));
1254 integral += geom.face_area(bdr) * quad_weight * psi_i * psi_j;
1271 template <
typename point_t,
1273 return_t func(
const point_t&,
const return_t),
1274 point_t fun(
const point_t&,
const return_t),
1275 typename smallVec_t = point_t>
1277 const unsigned int bdr,
1279 return_t f_param = 0.)
1281 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1282 return_t integral = 0., quad_weight, phi_i, winding;
1284 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
1286 point_t normal = geom.inner_normal(bdr);
1287 const unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
1289 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
1291 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
1294 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
1298 quad_pt[
dim] = (return_t)bdr_ind;
1308 winding =
scalar_product(normal, fun(geom.map_ref_to_phys(quad_pt), f_param));
1310 integral += geom.face_area(bdr) * quad_weight * phi_i *
1311 func(geom.map_ref_to_phys(quad_pt), f_param) * winding;
1328 template <
typename point_t,
1330 return_t func(
const point_t&,
const return_t),
1331 point_t fun(
const point_t&,
const return_t),
1332 typename smallVec_t = point_t>
1334 const unsigned int bdr,
1336 return_t f_param = 0.)
1338 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1339 return_t integral = 0., quad_weight, psi_i, winding;
1340 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_i =
1342 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
1344 point_t normal = geom.inner_normal(bdr);
1345 const unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
1347 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
1349 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
1352 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
1356 quad_pt[
dim] = (return_t)bdr_ind;
1365 winding =
scalar_product(normal, fun(geom.map_ref_to_phys(quad_pt), f_param));
1367 integral += geom.face_area(bdr) * quad_weight * psi_i *
1368 func(geom.map_ref_to_phys(quad_pt), f_param) * winding;
1388 template <
typename point_t,
1390 return_t fun(
const point_t&,
const return_t),
1391 typename smallVec_t = point_t>
1393 const unsigned int j,
1394 const unsigned int bdr,
1396 return_t f_param = 0.)
1398 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1399 return_t integral = 0., quad_weight, phi_j;
1402 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
1403 smallVec_t quad_pt, nabla_phi_i, normal;
1405 const unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
1407 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
1409 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
1413 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
1417 normal[
dim] = 2. * bdr_ind - 1.;
1418 quad_pt[
dim] = (return_t)bdr_ind;
1428 for (
unsigned int dim_fct = 0; dim_fct < geom_t::hyEdge_dim(); ++dim_fct)
1430 if (
dim == dim_fct &&
dim == bdr_dim)
1432 else if (
dim == dim_fct)
1434 else if (
dim == bdr_dim)
1440 integral += quad_weight * fun(geom.map_ref_to_phys(quad_pt), f_param) * phi_j *
1443 return geom.face_area(bdr) * integral;
1461 template <
typename point_t,
1463 return_t fun(
const point_t&,
const return_t),
1464 typename smallVec_t = point_t>
1466 const unsigned int j,
1467 const unsigned int bdr,
1469 return_t f_param = 0.)
1471 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1472 return_t integral = 0., quad_weight, phi_j;
1474 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_j =
1476 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
1477 smallVec_t quad_pt, nabla_phi_i, normal;
1479 const unsigned int bdr_dim = bdr / 2, bdr_ind = bdr % 2;
1481 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
1483 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
1487 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
1491 normal[
dim] = 2. * bdr_ind - 1.;
1492 quad_pt[
dim] = (return_t)bdr_ind;
1501 for (
unsigned int dim_fct = 0; dim_fct < geom_t::hyEdge_dim(); ++dim_fct)
1503 if (
dim == dim_fct &&
dim == bdr_dim)
1505 else if (
dim == dim_fct)
1507 else if (
dim == bdr_dim)
1513 integral += quad_weight * fun(geom.map_ref_to_phys(quad_pt), f_param) * phi_j *
1516 return geom.face_area(bdr) * integral;
1529 template <
typename geom_t>
1531 const unsigned int j,
1532 const unsigned int bdr,
1535 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1536 return_t integral = 1.;
1539 unsigned int dim = bdr / 2, bdr_ind = bdr % 2;
1540 for (
unsigned int dim_fct = 0; dim_fct < geom_t::hyEdge_dim(); ++dim_fct)
1546 return integral * geom.face_area(bdr);
1558 template <
typename geom_t>
1560 const unsigned int j,
1561 const unsigned int bdr,
1564 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1565 return_t integral = 1.;
1567 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_j =
1569 unsigned int dim = bdr / 2, bdr_ind = bdr % 2;
1570 for (
unsigned int dim_fct = 0; dim_fct < geom_t::hyEdge_dim(); ++dim_fct)
1575 return integral * geom.face_area(bdr);
1589 template <
typename point_t,
1591 return_t fun(
const point_t&,
const return_t),
1592 typename smallVec_t = point_t>
1594 const unsigned int bdr,
1596 const return_t f_param = 0.)
1598 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1599 return_t integral = 0., quad_val;
1601 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q;
1603 unsigned int dim_bdr = bdr / 2, bdr_ind = bdr % 2;
1605 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
1607 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
1609 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
1613 quad_pt[
dim] = bdr_ind;
1623 integral += fun(geom.map_ref_to_phys(quad_pt), f_param) * quad_val;
1625 return integral * geom.face_area(bdr);
1639 template <
typename point_t,
1641 return_t fun(
const point_t&,
const return_t),
1642 typename smallVec_t = point_t>
1644 const unsigned int bdr,
1646 const return_t f_param = 0.)
1648 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1649 return_t integral = 0., quad_val;
1650 std::array<
unsigned int, std::max(1U,
dim() - 1)> dec_q,
1653 unsigned int dim_bdr = bdr / 2, bdr_ind = bdr % 2;
1655 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim() - 1); ++q)
1657 dec_q =
Hypercube<
dim() - 1>::index_decompose(q, quadrature_t::n_points());
1659 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
1662 quad_pt[
dim] = bdr_ind;
1671 integral += fun(geom.map_ref_to_phys(quad_pt), f_param) * quad_val;
1686 template <
typename point_t,
1688 return_t fun(
const point_t&,
const return_t),
1689 typename smallVec_t = point_t,
1690 std::size_t n_coeff>
1693 const return_t f_param = 0.)
1695 static_assert(geom_t::hyEdge_dim() ==
dim(),
"Dimension of hyperedge must fit to quadrature!");
1696 return_t integral = 0., quad_weight;
1697 std::array<
unsigned int,
dim()> dec_i, dec_q;
1698 std::array<return_t, n_coeff> quad_val;
1701 for (
unsigned int q = 0; q < std::pow(
quad_weights.size(), geom_t::hyEdge_dim()); ++q)
1703 dec_q =
Hypercube<
dim()>::index_decompose(q, quadrature_t::n_points());
1706 for (
unsigned int dim = 0;
dim < geom_t::hyEdge_dim(); ++
dim)
1710 for (
unsigned int i = 0; i < n_coeff; ++i)
1716 integral += quad_weight * std::pow(fun(geom.map_ref_to_phys(quad_pt), f_param) -
1717 std::accumulate(quad_val.begin(), quad_val.end(), 0.),
1720 return integral * geom.area();