17 #include <deal.II/base/quadrature_lib.h> 18 #include <deal.II/base/qprojector.h> 19 #include <deal.II/base/thread_management.h> 20 #include <deal.II/base/utilities.h> 21 #include <deal.II/lac/vector.h> 22 #include <deal.II/lac/block_vector.h> 23 #include <deal.II/lac/parallel_vector.h> 24 #include <deal.II/lac/parallel_block_vector.h> 25 #include <deal.II/lac/petsc_parallel_vector.h> 26 #include <deal.II/lac/petsc_block_vector.h> 27 #include <deal.II/lac/petsc_parallel_block_vector.h> 28 #include <deal.II/lac/trilinos_vector.h> 29 #include <deal.II/lac/trilinos_block_vector.h> 30 #include <deal.II/lac/constraint_matrix.h> 31 #include <deal.II/grid/tria.h> 32 #include <deal.II/grid/tria_iterator.h> 33 #include <deal.II/grid/grid_generator.h> 34 #include <deal.II/fe/fe_tools.h> 35 #include <deal.II/fe/fe.h> 36 #include <deal.II/fe/fe_values.h> 37 #include <deal.II/dofs/dof_handler.h> 38 #include <deal.II/dofs/dof_accessor.h> 39 #include <deal.II/dofs/dof_tools.h> 40 #include <deal.II/hp/dof_handler.h> 42 #include <deal.II/base/std_cxx11/shared_ptr.h> 44 #include <deal.II/base/index_set.h> 49 DEAL_II_NAMESPACE_OPEN
53 template <
int dim,
int spacedim,
54 template <
int,
int>
class DoFHandlerType1,
55 template <
int,
int>
class DoFHandlerType2,
56 class InVector,
class OutVector>
60 const DoFHandlerType2<dim, spacedim> &dof2,
70 template <
int dim,
int spacedim,
71 template <
int,
int>
class DoFHandlerType1,
72 template <
int,
int>
class DoFHandlerType2,
73 class InVector,
class OutVector>
77 const DoFHandlerType2<dim, spacedim> &dof2,
81 Assert(&dof1.get_triangulation()==&dof2.get_triangulation(), ExcTriangulationMismatch());
83 Assert(u1.size()==dof1.n_dofs(),
84 ExcDimensionMismatch(u1.size(), dof1.n_dofs()));
85 Assert(u2.size()==dof2.n_dofs(),
86 ExcDimensionMismatch(u2.size(), dof2.n_dofs()));
89 const IndexSet &dof1_local_dofs = dof1.locally_owned_dofs();
90 const IndexSet &dof2_local_dofs = dof2.locally_owned_dofs();
91 const IndexSet u1_elements = u1.locally_owned_elements();
92 const IndexSet u2_elements = u2.locally_owned_elements();
93 Assert(u1_elements == dof1_local_dofs,
94 ExcMessage(
"The provided vector and DoF handler should have the same" 96 Assert(u2_elements == dof2_local_dofs,
97 ExcMessage(
"The provided vector and DoF handler should have the same" 112 std::map<const FiniteElement<dim,spacedim> *,
113 std::map<const FiniteElement<dim,spacedim> *,
114 std_cxx11::shared_ptr<FullMatrix<double> > > >
115 interpolation_matrices;
117 typename DoFHandlerType1<dim,spacedim>::active_cell_iterator cell1 = dof1.begin_active(),
119 typename DoFHandlerType2<dim,spacedim>::active_cell_iterator cell2 = dof2.begin_active(),
123 std::vector<types::global_dof_index> dofs;
124 dofs.reserve (DoFTools::max_dofs_per_cell (dof2));
127 OutVector touch_count(u2);
135 dof1.get_triangulation().locally_owned_subdomain();
137 for (; cell1!=endc1; ++cell1, ++cell2)
138 if ((cell1->subdomain_id() == subdomain_id)
142 Assert(cell1->get_fe().n_components() == cell2->get_fe().n_components(),
143 ExcDimensionMismatch (cell1->get_fe().n_components(),
144 cell2->get_fe().n_components()));
153 const bool hanging_nodes_not_allowed
154 = ((cell2->get_fe().dofs_per_vertex != 0) &&
157 if (hanging_nodes_not_allowed)
158 for (
unsigned int face=0; face<GeometryInfo<dim>::faces_per_cell; ++face)
159 Assert (cell1->at_boundary(face) ||
160 cell1->neighbor(face)->level() == cell1->level(),
161 ExcHangingNodesNotAllowed(0));
164 const unsigned int dofs_per_cell1 = cell1->get_fe().dofs_per_cell;
165 const unsigned int dofs_per_cell2 = cell2->get_fe().dofs_per_cell;
166 u1_local.
reinit (dofs_per_cell1);
167 u2_local.
reinit (dofs_per_cell2);
173 if (interpolation_matrices[&cell1->get_fe()][&cell2->get_fe()].get() == 0)
175 std_cxx11::shared_ptr<FullMatrix<double> >
178 interpolation_matrices[&cell1->get_fe()][&cell2->get_fe()]
179 = interpolation_matrix;
183 *interpolation_matrix);
186 cell1->get_dof_values(u1, u1_local);
187 interpolation_matrices[&cell1->get_fe()][&cell2->get_fe()]
188 ->vmult(u2_local, u1_local);
190 dofs.resize (dofs_per_cell2);
191 cell2->get_dof_indices(dofs);
193 for (
unsigned int i=0; i<dofs_per_cell2; ++i)
195 u2(dofs[i])+=u2_local(i);
196 touch_count(dofs[i]) += 1;
201 Assert (cell2 == endc2, ExcInternalError());
203 u2.compress(VectorOperation::add);
204 touch_count.compress(VectorOperation::add);
209 IndexSet locally_owned_dofs = dof2.locally_owned_dofs();
220 Assert(touch_count(i) !=
typename OutVector::value_type(),
222 u2(i) /= touch_count(i);
226 u2.compress(VectorOperation::insert);
233 template <
int dim,
class InVector,
class OutVector,
int spacedim>
238 OutVector &u1_interpolated)
244 ExcDimensionMismatch(u1_interpolated.size(), dof1.
n_dofs()));
248 const IndexSet u1_elements = u1.locally_owned_elements();
249 const IndexSet u1_interpolated_elements = u1_interpolated.locally_owned_elements();
250 Assert(u1_elements == dof1_local_dofs,
251 ExcMessage(
"The provided vector and DoF handler should have the same" 253 Assert(u1_interpolated_elements == dof1_local_dofs,
254 ExcMessage(
"The provided vector and DoF handler should have the same" 265 const bool hanging_nodes_not_allowed=
268 const unsigned int dofs_per_cell1=dof1.
get_fe().dofs_per_cell;
281 interpolation_matrix);
282 for (; cell!=endc; ++cell)
283 if ((cell->subdomain_id() == subdomain_id)
287 if (hanging_nodes_not_allowed)
288 for (
unsigned int face=0; face<GeometryInfo<dim>::faces_per_cell; ++face)
289 Assert (cell->at_boundary(face) ||
290 cell->neighbor(face)->level() == cell->level(),
291 ExcHangingNodesNotAllowed(0));
293 cell->get_dof_values(u1, u1_local);
294 interpolation_matrix.
vmult(u1_int_local, u1_local);
295 cell->set_dof_values(u1_int_local, u1_interpolated);
300 u1_interpolated.compress(VectorOperation::insert);
306 template <
int>
class DoFHandlerType,
307 class InVector,
class OutVector,
int spacedim>
312 OutVector &u1_interpolated)
314 Assert(u1.size() == dof1.n_dofs(),
315 ExcDimensionMismatch(u1.size(), dof1.n_dofs()));
316 Assert(u1_interpolated.size() == dof1.n_dofs(),
317 ExcDimensionMismatch(u1_interpolated.size(), dof1.n_dofs()));
320 const IndexSet &dof1_local_dofs = dof1.locally_owned_dofs();
321 const IndexSet u1_elements = u1.locally_owned_elements();
322 const IndexSet u1_interpolated_elements = u1_interpolated.locally_owned_elements();
323 Assert(u1_elements == dof1_local_dofs,
324 ExcMessage(
"The provided vector and DoF handler should have the same" 326 Assert(u1_interpolated_elements == dof1_local_dofs,
327 ExcMessage(
"The provided vector and DoF handler should have the same" 335 dof1.get_triangulation().locally_owned_subdomain();
337 typename DoFHandlerType<dim>::active_cell_iterator cell = dof1.begin_active(),
343 std::map<const FiniteElement<dim> *,
344 std_cxx11::shared_ptr<FullMatrix<double> > > interpolation_matrices;
346 for (; cell!=endc; ++cell)
347 if ((cell->subdomain_id() == subdomain_id)
352 ExcDimensionMismatch(cell->get_fe().n_components(),
362 const bool hanging_nodes_not_allowed=
365 if (hanging_nodes_not_allowed)
366 for (
unsigned int face=0; face<GeometryInfo<dim>::faces_per_cell; ++face)
367 Assert (cell->at_boundary(face) ||
368 cell->neighbor(face)->level() == cell->level(),
369 ExcHangingNodesNotAllowed(0));
371 const unsigned int dofs_per_cell1 = cell->get_fe().dofs_per_cell;
375 if (interpolation_matrices[&cell->get_fe()] != 0)
377 interpolation_matrices[&cell->get_fe()] =
378 std_cxx11::shared_ptr<FullMatrix<double> >
381 *interpolation_matrices[&cell->get_fe()]);
384 u1_local.
reinit (dofs_per_cell1);
385 u1_int_local.
reinit (dofs_per_cell1);
387 cell->get_dof_values(u1, u1_local);
388 interpolation_matrices[&cell->get_fe()]->vmult(u1_int_local, u1_local);
389 cell->set_dof_values(u1_int_local, u1_interpolated);
394 u1_interpolated.compress(VectorOperation::insert);
403 template <
int dim,
int spacedim,
class InVector>
409 InVector &u1_interpolated)
413 interpolate(dof2, u2, dof1, constraints1, u1_interpolated);
417 #ifdef DEAL_II_WITH_PETSC 418 template <
int dim,
int spacedim>
430 IndexSet dof2_locally_relevant_dofs;
432 dof2_locally_relevant_dofs);
438 dof2_locally_relevant_dofs,
441 interpolate(dof2, u2, dof1, constraints1, u1_interpolated);
446 #ifdef DEAL_II_WITH_TRILINOS 447 template <
int dim,
int spacedim>
459 IndexSet dof2_locally_relevant_dofs;
461 dof2_locally_relevant_dofs);
467 dof2_locally_relevant_dofs,
470 interpolate(dof2, u2, dof1, constraints1, u1_interpolated);
475 template <
int dim,
int spacedim,
typename Number>
484 IndexSet dof2_locally_relevant_dofs;
486 dof2_locally_relevant_dofs);
489 u2 (dof2_locally_owned_dofs,
490 dof2_locally_relevant_dofs,
494 u2.update_ghost_values ();
495 interpolate(dof2, u2, dof1, constraints1, u1_interpolated);
501 template <
int dim,
class InVector,
class OutVector,
int spacedim>
507 OutVector &u1_interpolated)
511 if (dof1.
get_fe().dofs_per_vertex==0 && dof2.
get_fe().dofs_per_vertex==0
517 ExcDimensionMismatch(dof1.
get_fe().n_components(), dof2.
get_fe().n_components()));
520 ExcDimensionMismatch(u1_interpolated.size(), dof1.
n_dofs()));
525 internal::back_interpolate(dof1, constraints1, u1, dof2, constraints2,
532 template <
int dim,
class InVector,
class OutVector,
int spacedim>
536 OutVector &u1_difference)
542 ExcDimensionMismatch(u1_difference.size(), dof1.
n_dofs()));
546 const IndexSet u1_elements = u1.locally_owned_elements();
547 const IndexSet u1_difference_elements = u1_difference.locally_owned_elements();
548 Assert(u1_elements == dof1_local_dofs,
549 ExcMessage(
"The provided vector and DoF handler should have the same" 551 Assert(u1_difference_elements == dof1_local_dofs,
552 ExcMessage(
"The provided vector and DoF handler should have the same" 563 const bool hanging_nodes_not_allowed=
566 const unsigned int dofs_per_cell=dof1.
get_fe().dofs_per_cell;
581 for (; cell!=endc; ++cell)
582 if ((cell->subdomain_id() == subdomain_id)
586 if (hanging_nodes_not_allowed)
587 for (
unsigned int face=0; face<GeometryInfo<dim>::faces_per_cell; ++face)
588 Assert (cell->at_boundary(face) ||
589 cell->neighbor(face)->level() == cell->level(),
590 ExcHangingNodesNotAllowed(0));
592 cell->get_dof_values(u1, u1_local);
593 difference_matrix.
vmult(u1_diff_local, u1_local);
594 cell->set_dof_values(u1_diff_local, u1_difference);
600 u1_difference.compress(VectorOperation::insert);
609 template <
int dim,
class InVector,
class OutVector,
int spacedim>
615 OutVector &u1_difference)
617 back_interpolate(dof1, constraints1, u1, dof2, constraints2, u1_difference);
618 u1_difference.sadd(-1, u1);
622 #ifdef DEAL_II_WITH_TRILINOS 623 template <
int dim,
int spacedim>
631 back_interpolate(dof1, constraints1, u1, dof2, constraints2, u1_difference);
639 u1_completely_distributed = u1;
641 u1_difference.
sadd(-1, u1_completely_distributed);
649 template <
int dim,
class InVector,
class OutVector,
int spacedim>
655 OutVector &u1_difference)
661 if (dof1.
get_fe().dofs_per_vertex==0 && dof2.
get_fe().dofs_per_vertex==0
666 internal::interpolation_difference(dof1, constraints1, u1, dof2, constraints2, u1_difference);
672 template <
int dim,
class InVector,
class OutVector,
int spacedim>
680 ExcDimensionMismatch(dof1.
get_fe().n_components(), dof2.
get_fe().n_components()));
688 const unsigned int n1 = dof1.
get_fe().dofs_per_cell;
689 const unsigned int n2 = dof2.
get_fe().dofs_per_cell;
693 std::vector<types::global_dof_index> dofs(n2);
701 cell1->get_dof_values(u1, u1_local);
702 matrix.
vmult(u2_local, u1_local);
703 cell2->get_dof_indices(dofs);
704 for (
unsigned int i=0; i<n2; ++i)
706 u2(dofs[i])+=u2_local(i);
715 template <
int dim,
class InVector,
class OutVector,
int spacedim>
728 template <
int dim,
class InVector,
class OutVector,
int spacedim>
736 ExcDimensionMismatch(dof1.
get_fe().n_components(), dof2.
get_fe().n_components()));
745 const unsigned int dofs_per_cell = dof2.
get_fe().dofs_per_cell;
756 for (; cell!=endc; ++cell)
757 Assert (cell->has_children(), ExcGridNotRefinedAtLeastOnce());
764 endc=dof2.
end(level);
766 for (; cell!=endc; ++cell)
772 bool active_children=
false;
773 for (
unsigned int child_n=0; child_n<cell->n_children(); ++child_n)
774 if (cell->child(child_n)->active())
776 active_children=
true;
789 cell->get_interpolated_dof_values(u3, dof_values);
790 cell->set_dof_values_by_interpolation(dof_values, u2);
804 #include "fe_tools_interpolate.inst" 809 DEAL_II_NAMESPACE_CLOSE
const MPI_Comm & get_mpi_communicator() const
const types::subdomain_id invalid_subdomain_id
cell_iterator begin(const unsigned int level=0) const
void sadd(const TrilinosScalar s, const VectorBase &V)
::ExceptionBase & ExcMessage(std::string arg1)
cell_iterator end() const
ActiveSelector::active_cell_iterator active_cell_iterator
const FiniteElement< dim, spacedim > & get_fe() const
void vmult(Vector< number2 > &w, const Vector< number2 > &v, const bool adding=false) const
active_cell_iterator begin_active(const unsigned int level=0) const
ActiveSelector::cell_iterator cell_iterator
unsigned int global_dof_index
#define Assert(cond, exc)
const Epetra_Map & vector_partitioner() const
size_type n_constraints() const
types::global_dof_index n_dofs() const
const MPI_Comm & get_mpi_communicator() const
unsigned int subdomain_id
void distribute(VectorType &vec) const
unsigned int n_components() const
const MPI_Comm & get_mpi_communicator() const
virtual void reinit(const size_type N, const bool omit_zeroing_entries=false)
const Triangulation< dim, spacedim > & get_triangulation() const
const unsigned int dofs_per_vertex
bool is_element(const size_type index) const
const IndexSet & locally_owned_dofs() const