17 #include <deal.II/base/std_cxx14/memory.h> 19 #include <deal.II/fe/fe_enriched.h> 20 #include <deal.II/fe/fe_tools.h> 23 DEAL_II_NAMESPACE_OPEN
36 std::vector<unsigned int>
37 build_multiplicities(
const std::vector<std::vector<T>> &functions)
39 std::vector<unsigned int> multiplicities;
40 multiplicities.push_back(1);
41 for (
unsigned int i = 0; i < functions.size(); i++)
42 multiplicities.push_back(functions[i].size());
44 return multiplicities;
51 template <
int dim,
int spacedim>
52 std::vector<const FiniteElement<dim, spacedim> *>
57 std::vector<const FiniteElement<dim, spacedim> *> fes;
58 fes.push_back(fe_base);
59 for (
unsigned int i = 0; i < fe_enriched.size(); i++)
60 fes.push_back(fe_enriched[i]);
70 template <
int dim,
int spacedim>
74 const std::vector<unsigned int> & multiplicities,
76 const typename ::Triangulation<dim, spacedim>::cell_iterator
82 "FEs and multiplicities should have the same size"));
90 const unsigned int n_comp_base = fes[0]->n_components();
93 for (
unsigned int fe = 1; fe < fes.size(); fe++)
101 "Only dominating FE_Nothing can be used in FE_Enriched"));
106 "All elements must have the same number of components"));
116 template <
int dim,
int spacedim>
122 for (
unsigned int fe = 1; fe < fes.size(); fe++)
134 template <
int dim,
int spacedim>
138 FE_Nothing<dim, spacedim>(fe_base.n_components(),
144 template <
int dim,
int spacedim>
153 const typename
Triangulation<dim, spacedim>::cell_iterator &)>>>(
156 const typename
Triangulation<dim, spacedim>::cell_iterator &)>>(
158 [=](const typename
Triangulation<dim, spacedim>::cell_iterator &)
159 -> const
Function<spacedim> * {
return enrichment_function; })))
163 template <
int dim,
int spacedim>
176 template <
int dim,
int spacedim>
179 const std::vector<unsigned int> & multiplicities,
183 FETools::Compositing::multiply_dof_numbers(fes, multiplicities, false),
184 FETools::Compositing::compute_restriction_is_additive_flags(
187 FETools::Compositing::compute_nonzero_components(fes,
196 Assert(internal::FE_Enriched::consistency_check(fes,
206 for (
unsigned int fe = 1; fe < fes.size(); fe++)
214 for (
unsigned int system_index = 0; system_index < this->
dofs_per_cell;
217 const unsigned int base_no =
222 const unsigned int base_m =
227 "Size mismatch for base_no_mult_local_enriched_dofs: " 230 "; base_no = " + std::to_string(base_no) +
231 "; base_m = " + std::to_string(base_m) +
232 "; system_index = " + std::to_string(system_index)));
243 for (
unsigned int base_no = 1;
247 for (
unsigned int m = 0;
251 fes[base_no]->dofs_per_cell,
254 fes[base_no]->dofs_per_cell));
259 template <
int dim,
int spacedim>
260 const std::vector<std::vector<std::function<const Function<spacedim> *(
268 template <
int dim,
int spacedim>
276 "For enriched finite elements shape_value() can not be defined on the reference element."));
281 template <
int dim,
int spacedim>
282 std::unique_ptr<FiniteElement<dim, spacedim>>
285 std::vector<const FiniteElement<dim, spacedim> *> fes;
286 std::vector<unsigned int> multiplicities;
294 return std::unique_ptr<FE_Enriched<dim, spacedim>>(
299 template <
int dim,
int spacedim>
322 template <
int dim,
int spacedim>
324 std::unique_ptr<typename FiniteElement<dim, spacedim>::InternalDataBase>
332 auto update_each_flags = fes_data->update_each;
333 auto data = std_cxx14::make_unique<InternalData>(std::move(fes_data));
336 data->update_each = update_each_flags;
341 const unsigned int n_q_points = quadrature.
size();
349 data->enrichment[base][m].values.resize(n_q_points);
352 data->enrichment[base][m].gradients.resize(n_q_points);
355 data->enrichment[base][m].hessians.resize(n_q_points);
359 return std::move(data);
363 template <
int dim,
int spacedim>
364 std::unique_ptr<typename FiniteElement<dim, spacedim>::InternalDataBase>
373 fe_system->get_face_data(update_flags, mapping, quadrature, output_data);
382 template <
int dim,
int spacedim>
383 std::unique_ptr<typename FiniteElement<dim, spacedim>::InternalDataBase>
393 fe_system->get_subface_data(update_flags, mapping, quadrature, output_data);
402 template <
int dim,
int spacedim>
403 std::unique_ptr<typename FiniteElement<dim, spacedim>::InternalDataBase>
411 auto data =
fe_system->get_data(flags, mapping, quadrature, output_data);
420 template <
int dim,
int spacedim>
424 const std::vector<unsigned int> & multiplicities)
426 Assert(fes.size() == multiplicities.size(),
433 for (
unsigned int i = 0; i < fes.size(); i++)
434 if (multiplicities[i] > 0)
476 fe_system->adjust_line_dof_index_for_line_orientation_table;
481 template <
int dim,
int spacedim>
485 std::ostringstream namebuf;
498 return namebuf.str();
502 template <
int dim,
int spacedim>
510 template <
int dim,
int spacedim>
518 const ::internal::FEValuesImplementation::MappingRelatedData<dim,
525 Assert(dynamic_cast<const InternalData *>(&fe_internal) !=
nullptr,
541 quadrature, fe_data, mapping_data, cell, output_data);
545 template <
int dim,
int spacedim>
549 const unsigned int face_no,
553 const ::internal::FEValuesImplementation::MappingRelatedData<dim,
560 Assert(dynamic_cast<const InternalData *>(&fe_internal) !=
nullptr,
576 quadrature, fe_data, mapping_data, cell, output_data);
580 template <
int dim,
int spacedim>
584 const unsigned int face_no,
585 const unsigned int sub_no,
589 const ::internal::FEValuesImplementation::MappingRelatedData<dim,
596 Assert(dynamic_cast<const InternalData *>(&fe_internal) !=
nullptr,
613 quadrature, fe_data, mapping_data, cell, output_data);
617 template <
int dim,
int spacedim>
639 const unsigned int n_q_points = quadrature.
size();
649 for (
unsigned int base_no = 1; base_no < this->
n_base_elements(); base_no++)
660 for (
unsigned int system_index = 0; system_index < this->
dofs_per_cell;
664 const unsigned int base_index =
674 unsigned int out_index = 0;
675 for (
unsigned int i = 0; i < system_index; ++i)
677 unsigned int in_index = 0;
678 for (
unsigned int i = 0; i < base_index; ++i)
685 for (
unsigned int s = 0;
690 for (
unsigned int q = 0; q < n_q_points; ++q)
692 base_data.shape_values(in_index + s, q);
695 for (
unsigned int q = 0; q < n_q_points; ++q)
697 base_data.shape_gradients[in_index + s][q];
700 for (
unsigned int q = 0; q < n_q_points; ++q)
702 base_data.shape_hessians[in_index + s][q];
711 for (
unsigned int base_no = 1; base_no < this->
n_base_elements(); base_no++)
718 for (
unsigned int m = 0;
729 ExcMessage(
"The pointer to the enrichment function is NULL"));
733 "Only scalar-valued enrichment functions are allowed"));
740 fe_data.
enrichment[base_no][m].hessians.size(),
742 for (
unsigned int q = 0; q < n_q_points; q++)
753 fe_data.
enrichment[base_no][m].gradients.size(),
755 for (
unsigned int q = 0; q < n_q_points; q++)
767 for (
unsigned int q = 0; q < n_q_points; q++)
786 for (
unsigned int m = 0;
789 for (
unsigned int i = 0;
793 const unsigned int enriched_dof =
795 for (
unsigned int q = 0; q < n_q_points; ++q)
815 for (
unsigned int base_no = 1; base_no < this->
n_base_elements(); base_no++)
817 for (
unsigned int m = 0;
820 for (
unsigned int i = 0;
824 const unsigned int enriched_dof =
826 for (
unsigned int q = 0; q < n_q_points; ++q)
838 for (
unsigned int base_no = 1; base_no < this->
n_base_elements(); base_no++)
840 for (
unsigned int m = 0;
843 for (
unsigned int i = 0;
847 const unsigned int enriched_dof =
849 for (
unsigned int q = 0; q < n_q_points; ++q)
859 template <
int dim,
int spacedim>
867 template <
int dim,
int spacedim>
875 template <
int dim,
int spacedim>
884 fe_system->get_face_interpolation_matrix(fe_enr_other->get_fe_system(),
897 template <
int dim,
int spacedim>
901 const unsigned int subface,
907 fe_system->get_subface_interpolation_matrix(fe_enr_other->get_fe_system(),
921 template <
int dim,
int spacedim>
922 std::vector<std::pair<unsigned int, unsigned int>>
929 return fe_system->hp_vertex_dof_identities(fe_enr_other->get_fe_system());
934 return std::vector<std::pair<unsigned int, unsigned int>>();
939 template <
int dim,
int spacedim>
940 std::vector<std::pair<unsigned int, unsigned int>>
947 return fe_system->hp_line_dof_identities(fe_enr_other->get_fe_system());
952 return std::vector<std::pair<unsigned int, unsigned int>>();
957 template <
int dim,
int spacedim>
958 std::vector<std::pair<unsigned int, unsigned int>>
965 return fe_system->hp_quad_dof_identities(fe_enr_other->get_fe_system());
970 return std::vector<std::pair<unsigned int, unsigned int>>();
975 template <
int dim,
int spacedim>
993 return fe_system->compare_for_face_domination(
994 fe_enr_other->get_fe_system());
1003 template <
int dim,
int spacedim>
1006 const unsigned int child,
1009 return fe_system->get_prolongation_matrix(child, refinement_case);
1013 template <
int dim,
int spacedim>
1016 const unsigned int child,
1019 return fe_system->get_restriction_matrix(child, refinement_case);
1026 template <
int dim,
int spacedim>
1029 : fesystem_data(
std::move(fesystem_data))
1033 template <
int dim,
int spacedim>
1036 const unsigned int base_no)
const 1042 template <
int dim,
int spacedim>
1045 const unsigned int base_no)
const 1052 #include "fe_enriched.inst" 1054 DEAL_II_NAMESPACE_CLOSE
virtual const FiniteElement< dim, spacedim > & base_element(const unsigned int index) const override
virtual std::vector< std::pair< unsigned int, unsigned int > > hp_line_dof_identities(const FiniteElement< dim, spacedim > &fe_other) const override
virtual void get_face_interpolation_matrix(const FiniteElement< dim, spacedim > &source, FullMatrix< double > &matrix) const override
FullMatrix< double > interface_constraints
virtual const FullMatrix< double > & get_restriction_matrix(const unsigned int child, const RefinementCase< dim > &refinement_case=RefinementCase< dim >::isotropic_refinement) const override
InternalData(std::unique_ptr< typename FESystem< dim, spacedim >::InternalData > fesystem_data)
FE_Enriched(const FiniteElement< dim, spacedim > &fe_base, const FiniteElement< dim, spacedim > &fe_enriched, const Function< spacedim > *enrichment_function)
const std::vector< std::vector< std::function< const Function< spacedim > *(const typename Triangulation< dim, spacedim >::cell_iterator &)> > > get_enrichments() const
bool is_dominating() const
SymmetricTensor< 4, dim, Number > outer_product(const SymmetricTensor< 2, dim, Number > &t1, const SymmetricTensor< 2, dim, Number > &t2)
virtual FiniteElementDomination::Domination compare_for_face_domination(const FiniteElement< dim, spacedim > &fe_other) const override
std::vector< std::pair< std::pair< unsigned int, unsigned int >, unsigned int > > component_to_base_table
std::vector< std::vector< EnrichmentValues > > enrichment
std::unique_ptr< typename FiniteElement< dim, spacedim >::InternalDataBase > setup_data(std::unique_ptr< typename FESystem< dim, spacedim >::InternalData > fes_data, const UpdateFlags flags, const Quadrature< dim_1 > &quadrature) const
std::vector< Point< dim-1 > > unit_face_support_points
Transformed quadrature points.
#define AssertThrow(cond, exc)
static::ExceptionBase & ExcInterpolationNotImplemented()
std::unique_ptr< To > dynamic_unique_cast(std::unique_ptr< From > &&p)
void multiply_by_enrichment(const Quadrature< dim_1 > &quadrature, const InternalData &fe_data, const internal::FEValuesImplementation::MappingRelatedData< dim, spacedim > &mapping_data, const typename Triangulation< dim, spacedim >::cell_iterator &cell, internal::FEValuesImplementation::FiniteElementRelatedData< dim, spacedim > &output_data) const
std::vector< Point< dim > > unit_support_points
virtual std::vector< std::pair< unsigned int, unsigned int > > hp_vertex_dof_identities(const FiniteElement< dim, spacedim > &fe_other) const override
virtual std::string get_name() const override
const std::vector< std::vector< std::function< const Function< spacedim > *(const typename Triangulation< dim, spacedim >::cell_iterator &)> > > enrichments
unsigned int element_multiplicity(const unsigned int index) const
unsigned int size() const
static::ExceptionBase & ExcMessage(std::string arg1)
void initialize(const std::vector< const FiniteElement< dim, spacedim > * > &fes, const std::vector< unsigned int > &multiplicities)
std::unique_ptr< typename FESystem< dim, spacedim >::InternalData > fesystem_data
Third derivatives of shape functions.
const std::unique_ptr< const FESystem< dim, spacedim > > fe_system
#define Assert(cond, exc)
unsigned int n_nonzero_components(const unsigned int i) const
static::ExceptionBase & ExcDimensionMismatch(std::size_t arg1, std::size_t arg2)
Abstract base class for mapping classes.
void reinit(const unsigned int n_blocks, const size_type n_elements_per_block)
virtual std::unique_ptr< typename FiniteElement< dim, spacedim >::InternalDataBase > get_data(const UpdateFlags flags, const Mapping< dim, spacedim > &mapping, const Quadrature< dim > &quadrature,::internal::FEValuesImplementation::FiniteElementRelatedData< dim, spacedim > &output_data) const override
unsigned int n_base_elements() const
SymmetricTensor< 2, dim, Number > symmetrize(const Tensor< 2, dim, Number > &t)
unsigned int n_components() const
Second derivatives of shape functions.
internal::FEValuesImplementation::FiniteElementRelatedData< dim, spacedim > & get_fe_output_object(const unsigned int base_no) const
virtual double shape_value(const unsigned int i, const Point< dim > &p) const override
std::string dim_string(const int dim, const int spacedim)
virtual UpdateFlags requires_update_flags(const UpdateFlags update_flags) const override
const unsigned int dofs_per_cell
virtual const FullMatrix< double > & get_prolongation_matrix(const unsigned int child, const RefinementCase< dim > &refinement_case=RefinementCase< dim >::isotropic_refinement) const override
virtual void get_subface_interpolation_matrix(const FiniteElement< dim, spacedim > &source, const unsigned int subface, FullMatrix< double > &matrix) const override
Shape function gradients.
std::vector< std::vector< std::vector< unsigned int > > > base_no_mult_local_enriched_dofs
std::vector< std::pair< unsigned int, unsigned int > > system_to_component_table
void push_back(const size_type size)
const unsigned int dofs_per_face
std::vector< std::pair< std::pair< unsigned int, unsigned int >, unsigned int > > system_to_base_table
static::ExceptionBase & ExcNotImplemented()
std::vector< std::pair< unsigned int, unsigned int > > face_system_to_component_table
virtual std::unique_ptr< FiniteElement< dim, spacedim > > clone() const override
const FESystem< dim, spacedim > & get_fe_system() const
BlockIndices base_to_block_indices
std::vector< std::pair< std::pair< unsigned int, unsigned int >, unsigned int > > face_system_to_base_table
virtual std::vector< std::pair< unsigned int, unsigned int > > hp_quad_dof_identities(const FiniteElement< dim, spacedim > &fe_other) const override
virtual std::unique_ptr< typename FiniteElement< dim, spacedim >::InternalDataBase > get_subface_data(const UpdateFlags update_flags, const Mapping< dim, spacedim > &mapping, const Quadrature< dim-1 > &quadrature,::internal::FEValuesImplementation::FiniteElementRelatedData< dim, spacedim > &output_data) const override
std::vector< int > adjust_line_dof_index_for_line_orientation_table
FiniteElement< dim, spacedim >::InternalDataBase & get_fe_data(const unsigned int base_no) const
virtual bool hp_constraints_are_implemented() const override
virtual std::unique_ptr< typename FiniteElement< dim, spacedim >::InternalDataBase > get_face_data(const UpdateFlags update_flags, const Mapping< dim, spacedim > &mapping, const Quadrature< dim-1 > &quadrature,::internal::FEValuesImplementation::FiniteElementRelatedData< dim, spacedim > &output_data) const override
static::ExceptionBase & ExcInternalError()