16 #include <deal.II/base/thread_management.h> 17 #include <deal.II/base/utilities.h> 18 #include <deal.II/base/quadrature_lib.h> 19 #include <deal.II/base/types.h> 20 #include <deal.II/base/template_constraints.h> 22 #include <deal.II/lac/sparsity_pattern.h> 23 #include <deal.II/lac/sparsity_tools.h> 24 #include <deal.II/lac/dynamic_sparsity_pattern.h> 25 #include <deal.II/lac/constraint_matrix.h> 27 #include <deal.II/dofs/dof_accessor.h> 28 #include <deal.II/dofs/dof_handler.h> 29 #include <deal.II/dofs/dof_tools.h> 30 #include <deal.II/dofs/dof_renumbering.h> 32 #include <deal.II/grid/tria_iterator.h> 33 #include <deal.II/grid/tria.h> 35 #include <deal.II/fe/fe.h> 36 #include <deal.II/hp/dof_handler.h> 37 #include <deal.II/hp/fe_collection.h> 38 #include <deal.II/hp/fe_values.h> 40 #include <deal.II/multigrid/mg_tools.h> 42 #include <deal.II/distributed/tria.h> 44 #include <boost/config.hpp> 45 #include <boost/graph/adjacency_list.hpp> 46 #include <boost/graph/cuthill_mckee_ordering.hpp> 47 #include <boost/graph/king_ordering.hpp> 48 #include <boost/graph/minimum_degree_ordering.hpp> 49 #include <boost/graph/properties.hpp> 50 #include <boost/graph/bandwidth.hpp> 51 DEAL_II_DISABLE_EXTRA_DIAGNOSTICS
52 #include <boost/random.hpp> 53 #include <boost/random/uniform_int_distribution.hpp> 63 DEAL_II_NAMESPACE_OPEN
71 using namespace ::boost;
74 typedef adjacency_list<vecS, vecS, undirectedS,
75 property<vertex_color_t, default_color_type,
76 property<vertex_degree_t,int> > > Graph;
77 typedef graph_traits<Graph>::vertex_descriptor Vertex;
78 typedef graph_traits<Graph>::vertices_size_type
size_type;
80 typedef std::pair<size_type, size_type> Pair;
86 template <
typename DoFHandlerType>
88 (
const DoFHandlerType &dof_handler,
89 const bool use_constraints,
90 boosttypes::Graph &graph,
91 boosttypes::property_map<boosttypes::Graph,boosttypes::vertex_degree_t>::type &graph_degree)
100 constraints.
close ();
102 dof_handler.n_dofs());
106 for (
unsigned int row=0; row<dsp.n_rows(); ++row)
107 for (
unsigned int col=0; col < dsp.row_length(row); ++col)
108 add_edge (row, dsp.column_number (row, col), graph);
111 boosttypes::graph_traits<boosttypes::Graph>::vertex_iterator ui, ui_end;
113 graph_degree =
get(::boost::vertex_degree, graph);
114 for (::boost::tie(ui, ui_end) = vertices(graph); ui != ui_end; ++ui)
115 graph_degree[*ui] = degree(*ui, graph);
120 template <
typename DoFHandlerType>
123 const bool reversed_numbering,
124 const bool use_constraints)
126 std::vector<types::global_dof_index> renumbering(dof_handler.n_dofs(),
127 DoFHandlerType::invalid_dof_index);
134 dof_handler.renumber_dofs (renumbering);
138 template <
typename DoFHandlerType>
141 const DoFHandlerType &dof_handler,
142 const bool reversed_numbering,
143 const bool use_constraints)
146 graph(dof_handler.n_dofs());
147 boosttypes::property_map<boosttypes::Graph,boosttypes::vertex_degree_t>::type
150 internal::create_graph (dof_handler, use_constraints, graph, graph_degree);
152 boosttypes::property_map<boosttypes::Graph, boosttypes::vertex_index_t>::type
153 index_map =
get(::boost::vertex_index, graph);
156 std::vector<boosttypes::Vertex> inv_perm(num_vertices(graph));
158 if (reversed_numbering ==
false)
159 ::boost::cuthill_mckee_ordering(graph, inv_perm.rbegin(),
160 get(::boost::vertex_color, graph),
161 make_degree_map(graph));
163 ::boost::cuthill_mckee_ordering(graph, inv_perm.begin(),
164 get(::boost::vertex_color, graph),
165 make_degree_map(graph));
167 for (boosttypes::size_type c = 0; c != inv_perm.size(); ++c)
168 new_dof_indices[index_map[inv_perm[c]]] = c;
170 Assert (std::find (new_dof_indices.begin(), new_dof_indices.end(),
171 DoFHandlerType::invalid_dof_index) == new_dof_indices.end(),
177 template <
typename DoFHandlerType>
180 const bool reversed_numbering,
181 const bool use_constraints)
183 std::vector<types::global_dof_index> renumbering(dof_handler.n_dofs(),
184 DoFHandlerType::invalid_dof_index);
191 dof_handler.renumber_dofs (renumbering);
195 template <
typename DoFHandlerType>
198 const DoFHandlerType &dof_handler,
199 const bool reversed_numbering,
200 const bool use_constraints)
203 graph(dof_handler.n_dofs());
204 boosttypes::property_map<boosttypes::Graph,boosttypes::vertex_degree_t>::type
207 internal::create_graph (dof_handler, use_constraints, graph, graph_degree);
209 boosttypes::property_map<boosttypes::Graph, boosttypes::vertex_index_t>::type
210 index_map =
get(::boost::vertex_index, graph);
213 std::vector<boosttypes::Vertex> inv_perm(num_vertices(graph));
215 if (reversed_numbering ==
false)
216 ::boost::king_ordering(graph, inv_perm.rbegin());
218 ::boost::king_ordering(graph, inv_perm.begin());
220 for (boosttypes::size_type c = 0; c != inv_perm.size(); ++c)
221 new_dof_indices[index_map[inv_perm[c]]] = c;
223 Assert (std::find (new_dof_indices.begin(), new_dof_indices.end(),
224 DoFHandlerType::invalid_dof_index) == new_dof_indices.end(),
230 template <
typename DoFHandlerType>
233 const bool reversed_numbering,
234 const bool use_constraints)
236 std::vector<types::global_dof_index> renumbering(dof_handler.n_dofs(),
237 DoFHandlerType::invalid_dof_index);
244 dof_handler.renumber_dofs (renumbering);
248 template <
typename DoFHandlerType>
251 const DoFHandlerType &dof_handler,
252 const bool reversed_numbering,
253 const bool use_constraints)
255 (void)use_constraints;
256 Assert (use_constraints ==
false, ExcNotImplemented());
264 using namespace ::boost;
271 typedef adjacency_list<vecS, vecS, directedS> Graph;
272 typedef graph_traits<Graph>::vertex_descriptor Vertex;
274 int n = dof_handler.n_dofs();
278 std::vector<::types::global_dof_index> dofs_on_this_cell;
280 typename DoFHandlerType::active_cell_iterator cell = dof_handler.begin_active(),
281 endc = dof_handler.end();
283 for (; cell!=endc; ++cell)
286 const unsigned int dofs_per_cell = cell->get_fe().dofs_per_cell;
288 dofs_on_this_cell.resize (dofs_per_cell);
290 cell->get_active_or_mg_dof_indices (dofs_on_this_cell);
291 for (
unsigned int i=0; i<dofs_per_cell; ++i)
292 for (
unsigned int j=0; j<dofs_per_cell; ++j)
293 if (dofs_on_this_cell[i] > dofs_on_this_cell[j])
295 add_edge (dofs_on_this_cell[i], dofs_on_this_cell[j], G);
296 add_edge (dofs_on_this_cell[j], dofs_on_this_cell[i], G);
301 typedef std::vector<int>
Vector;
304 Vector inverse_perm(n, 0);
309 Vector supernode_sizes(n, 1);
312 ::boost::property_map<Graph, vertex_index_t>::type
313 id =
get(vertex_index, G);
319 minimum_degree_ordering
321 make_iterator_property_map(°ree[0],
id, degree[0]),
324 make_iterator_property_map(&supernode_sizes[0],
id, supernode_sizes[0]),
328 for (
int i=0; i<n; ++i)
334 != inverse_perm.
end(),
336 Assert (inverse_perm[perm[i]] == i, ExcInternalError());
339 if (reversed_numbering ==
true)
340 std::copy (perm.
begin(), perm.
end(),
341 new_dof_indices.begin());
343 std::copy (inverse_perm.
begin(), inverse_perm.
end(),
344 new_dof_indices.begin());
351 template <
typename DoFHandlerType>
354 const bool reversed_numbering,
355 const bool use_constraints,
356 const std::vector<types::global_dof_index> &starting_indices)
358 std::vector<types::global_dof_index> renumbering(dof_handler.locally_owned_dofs().n_elements(),
359 DoFHandlerType::invalid_dof_index);
361 use_constraints, starting_indices);
366 dof_handler.renumber_dofs (renumbering);
371 template <
typename DoFHandlerType>
374 const DoFHandlerType &dof_handler,
375 const bool reversed_numbering,
376 const bool use_constraints,
377 const std::vector<types::global_dof_index> &starting_indices)
380 if (dof_handler.locally_owned_dofs().n_elements() == 0)
382 Assert (new_indices.size() == 0, ExcInternalError());
396 constraints.
close ();
398 const IndexSet locally_owned = dof_handler.locally_owned_dofs();
402 dof_handler.n_dofs(),
407 constraints.
clear ();
412 locally_owned.
size())
418 std::vector<types::global_dof_index> row_entries;
419 for (
unsigned int i=0; i<locally_owned.
n_elements(); ++i)
424 dsp.begin(row); it != dsp.end(row); ++it)
425 if (it->column() != row && locally_owned.
is_element(it->column()))
427 sparsity.add_entries(i, row_entries.begin(), row_entries.end(),
432 std::vector<types::global_dof_index> local_starting_indices (starting_indices.size());
433 for (
unsigned int i=0; i<starting_indices.size(); ++i)
436 ExcMessage (
"You specified global degree of freedom " 438 " as a starting index, but this index is not among the " 439 "locally owned ones on this processor."));
440 local_starting_indices[i] = locally_owned.
index_within_set(starting_indices[i]);
446 local_starting_indices);
447 if (reversed_numbering)
451 for (std::size_t i=0; i<new_indices.size(); ++i)
459 if (reversed_numbering)
466 template <
typename DoFHandlerType>
468 const unsigned int level,
469 const bool reversed_numbering,
470 const std::vector<types::global_dof_index> &starting_indices)
473 ExcNotInitialized());
477 dof_handler.n_dofs(level));
480 std::vector<types::global_dof_index> new_indices(dsp.n_rows());
484 if (reversed_numbering)
490 dof_handler.renumber_dofs (level, new_indices);
495 template <
int dim,
int spacedim>
498 const std::vector<unsigned int> &component_order_arg)
505 const typename DoFHandler<dim,spacedim>::level_cell_iterator
506 end = dof_handler.
end();
511 typename DoFHandler<dim,spacedim>::level_cell_iterator>
512 (renumbering, start, end, component_order_arg,
false);
527 (result <= dof_handler.
n_dofs())),
528 ExcRenumberingIncomplete());
542 const std::vector<unsigned int> &component_order_arg)
545 std::vector<types::global_dof_index> renumbering (dof_handler.
n_dofs(),
550 const typename hp::DoFHandler<dim>::level_cell_iterator
551 end = dof_handler.
end();
556 typename hp::DoFHandler<dim>::level_cell_iterator>
557 (renumbering, start, end, component_order_arg,
false);
559 if (result == 0)
return;
562 ExcRenumberingIncomplete());
569 template <
typename DoFHandlerType>
572 const unsigned int level,
573 const std::vector<unsigned int> &component_order_arg)
576 ExcNotInitialized());
578 std::vector<types::global_dof_index> renumbering (dof_handler.n_dofs(level),
579 DoFHandlerType::invalid_dof_index);
581 typename DoFHandlerType::level_cell_iterator start =dof_handler.begin(level);
582 typename DoFHandlerType::level_cell_iterator end = dof_handler.end(level);
586 typename DoFHandlerType::level_cell_iterator,
typename DoFHandlerType::level_cell_iterator>
587 (renumbering, start, end, component_order_arg,
true);
589 if (result == 0)
return;
591 Assert (result == dof_handler.n_dofs(level),
592 ExcRenumberingIncomplete());
594 if (renumbering.size()!=0)
595 dof_handler.renumber_dofs (level, renumbering);
600 template <
int dim,
int spacedim,
class ITERATOR,
class ENDITERATOR>
603 const ITERATOR &start,
604 const ENDITERATOR &end,
605 const std::vector<unsigned int> &component_order_arg,
606 bool is_level_operation)
609 fe_collection (start->get_dof_handler().get_fe ());
613 if (fe_collection.n_components() == 1)
615 new_indices.resize(0);
621 std::vector<unsigned int> component_order (component_order_arg);
626 if (component_order.size() == 0)
627 for (
unsigned int i=0; i<fe_collection.n_components(); ++i)
628 component_order.push_back (i);
630 Assert (component_order.size() == fe_collection.n_components(),
631 ExcDimensionMismatch(component_order.size(), fe_collection.n_components()));
633 for (
unsigned int i=0; i<component_order.size(); ++i)
634 Assert(component_order[i] < fe_collection.n_components(),
635 ExcIndexRange(component_order[i], 0, fe_collection.n_components()));
639 std::vector<types::global_dof_index> local_dof_indices;
651 std::vector<std::vector<unsigned int> > component_list (fe_collection.size());
652 for (
unsigned int f=0; f<fe_collection.size(); ++f)
656 component_list[f].resize(dofs_per_cell);
657 for (
unsigned int i=0; i<dofs_per_cell; ++i)
663 const unsigned int comp
669 component_list[f][i] = component_order[comp];
684 std::vector<std::vector<types::global_dof_index> >
685 component_to_dof_map (fe_collection.n_components());
686 for (ITERATOR cell=start; cell!=end; ++cell)
688 if (is_level_operation)
691 if (!cell->is_locally_owned_on_level())
698 if (!cell->is_locally_owned())
704 const unsigned int fe_index = cell->active_fe_index();
705 const unsigned int dofs_per_cell = fe_collection[fe_index].dofs_per_cell;
706 local_dof_indices.resize (dofs_per_cell);
707 cell->get_active_or_mg_dof_indices (local_dof_indices);
708 for (
unsigned int i=0; i<dofs_per_cell; ++i)
709 if (start->get_dof_handler().locally_owned_dofs().is_element(local_dof_indices[i]))
710 component_to_dof_map[component_list[fe_index][i]].
711 push_back (local_dof_indices[i]);
737 for (
unsigned int component=0; component<fe_collection.n_components();
740 std::sort (component_to_dof_map[component].begin(),
741 component_to_dof_map[component].end());
742 component_to_dof_map[component]
743 .erase (std::unique (component_to_dof_map[component].begin(),
744 component_to_dof_map[component].end()),
745 component_to_dof_map[component].end());
750 const unsigned int n_buckets = fe_collection.n_components();
751 std::vector<types::global_dof_index> shifts(n_buckets);
755 (&start->get_dof_handler().get_triangulation())))
757 #ifdef DEAL_II_WITH_MPI 758 std::vector<types::global_dof_index> local_dof_count(n_buckets);
760 for (
unsigned int c=0; c<n_buckets; ++c)
761 local_dof_count[c] = component_to_dof_map[c].size();
765 std::vector<types::global_dof_index>
766 all_dof_counts(fe_collection.n_components() *
769 MPI_Allgather ( &local_dof_count[0],
770 n_buckets, DEAL_II_DOF_INDEX_MPI_TYPE,
772 n_buckets, DEAL_II_DOF_INDEX_MPI_TYPE,
773 tria->get_communicator());
775 for (
unsigned int i=0; i<n_buckets; ++i)
776 Assert (all_dof_counts[n_buckets*tria->locally_owned_subdomain()+i]
782 unsigned int cumulated = 0;
783 for (
unsigned int c=0; c<n_buckets; ++c)
787 shifts[c] += all_dof_counts[c+n_buckets*i];
789 cumulated += all_dof_counts[c+n_buckets*i];
793 Assert (
false, ExcInternalError());
799 for (
unsigned int c=1; c<fe_collection.n_components(); ++c)
800 shifts[c] = shifts[c-1] + component_to_dof_map[c-1].size();
810 for (
unsigned int component=0; component<fe_collection.n_components(); ++component)
812 const typename std::vector<types::global_dof_index>::const_iterator
813 begin_of_component = component_to_dof_map[component].begin(),
814 end_of_component = component_to_dof_map[component].end();
816 next_free_index = shifts[component];
818 for (
typename std::vector<types::global_dof_index>::const_iterator
819 dof_index = begin_of_component;
820 dof_index != end_of_component; ++dof_index)
822 Assert (start->get_dof_handler().locally_owned_dofs()
823 .index_within_set(*dof_index)
827 new_indices[start->get_dof_handler().locally_owned_dofs()
828 .index_within_set(*dof_index)]
833 return next_free_index;
838 template <
int dim,
int spacedim>
847 const typename DoFHandler<dim,spacedim>::level_cell_iterator
848 end = dof_handler.
end();
851 compute_block_wise<dim, spacedim, typename DoFHandler<dim,spacedim>::active_cell_iterator,
852 typename DoFHandler<dim,spacedim>::level_cell_iterator>
853 (renumbering, start, end,
false);
868 (result <= dof_handler.
n_dofs())),
869 ExcRenumberingIncomplete());
876 template <
int dim,
int spacedim>
880 std::vector<types::global_dof_index> renumbering (dof_handler.
n_dofs(),
885 const typename hp::DoFHandler<dim,spacedim>::level_cell_iterator
886 end = dof_handler.
end();
889 compute_block_wise<dim, spacedim, typename hp::DoFHandler<dim,spacedim>::active_cell_iterator,
890 typename hp::DoFHandler<dim,spacedim>::level_cell_iterator>(renumbering,
897 ExcRenumberingIncomplete());
904 template <
int dim,
int spacedim>
909 ExcNotInitialized());
911 std::vector<types::global_dof_index> renumbering (dof_handler.
n_dofs(level),
914 typename DoFHandler<dim, spacedim>::level_cell_iterator
915 start =dof_handler.
begin(level);
916 typename DoFHandler<dim, spacedim>::level_cell_iterator
917 end = dof_handler.
end(level);
920 compute_block_wise<dim, spacedim, typename DoFHandler<dim, spacedim>::level_cell_iterator,
921 typename DoFHandler<dim, spacedim>::level_cell_iterator>(
922 renumbering, start, end,
true);
924 if (result == 0)
return;
927 ExcRenumberingIncomplete());
929 if (renumbering.size()!=0)
935 template <
int dim,
int spacedim,
class ITERATOR,
class ENDITERATOR>
938 const ITERATOR &start,
939 const ENDITERATOR &end,
940 const bool is_level_operation)
943 fe_collection (start->get_dof_handler().get_fe ());
947 if (fe_collection.n_blocks() == 1)
949 new_indices.resize(0);
955 std::vector<types::global_dof_index> local_dof_indices;
960 std::vector<std::vector<types::global_dof_index> > block_list (fe_collection.size());
961 for (
unsigned int f=0; f<fe_collection.size(); ++f)
981 std::vector<std::vector<types::global_dof_index> >
982 block_to_dof_map (fe_collection.n_blocks());
983 for (ITERATOR cell=start; cell!=end; ++cell)
985 if (is_level_operation)
988 if (!cell->is_locally_owned_on_level())
995 if (!cell->is_locally_owned())
1002 const unsigned int fe_index = cell->active_fe_index();
1003 const unsigned int dofs_per_cell =fe_collection[fe_index].dofs_per_cell;
1004 local_dof_indices.resize (dofs_per_cell);
1005 cell->get_active_or_mg_dof_indices (local_dof_indices);
1006 for (
unsigned int i=0; i<dofs_per_cell; ++i)
1007 if (start->get_dof_handler().locally_owned_dofs().is_element(local_dof_indices[i]))
1008 block_to_dof_map[block_list[fe_index][i]].
1009 push_back (local_dof_indices[i]);
1024 for (
unsigned int block=0; block<fe_collection.n_blocks();
1027 std::sort (block_to_dof_map[block].begin(),
1028 block_to_dof_map[block].end());
1029 block_to_dof_map[block]
1030 .erase (std::unique (block_to_dof_map[block].begin(),
1031 block_to_dof_map[block].end()),
1032 block_to_dof_map[block].end());
1037 const unsigned int n_buckets = fe_collection.n_blocks();
1038 std::vector<types::global_dof_index> shifts(n_buckets);
1042 (&start->get_dof_handler().get_triangulation())))
1044 #ifdef DEAL_II_WITH_MPI 1045 std::vector<types::global_dof_index> local_dof_count(n_buckets);
1047 for (
unsigned int c=0; c<n_buckets; ++c)
1048 local_dof_count[c] = block_to_dof_map[c].size();
1052 std::vector<types::global_dof_index>
1053 all_dof_counts(fe_collection.n_components() *
1056 MPI_Allgather ( &local_dof_count[0],
1057 n_buckets, DEAL_II_DOF_INDEX_MPI_TYPE,
1059 n_buckets, DEAL_II_DOF_INDEX_MPI_TYPE,
1060 tria->get_communicator());
1062 for (
unsigned int i=0; i<n_buckets; ++i)
1063 Assert (all_dof_counts[n_buckets*tria->locally_owned_subdomain()+i]
1066 ExcInternalError());
1070 for (
unsigned int c=0; c<n_buckets; ++c)
1072 shifts[c]=cumulated;
1074 shifts[c] += all_dof_counts[c+n_buckets*i];
1076 cumulated += all_dof_counts[c+n_buckets*i];
1080 Assert (
false, ExcInternalError());
1086 for (
unsigned int c=1; c<fe_collection.n_blocks(); ++c)
1087 shifts[c] = shifts[c-1] + block_to_dof_map[c-1].size();
1097 for (
unsigned int block=0; block<fe_collection.n_blocks(); ++block)
1099 const typename std::vector<types::global_dof_index>::const_iterator
1100 begin_of_component = block_to_dof_map[block].begin(),
1101 end_of_component = block_to_dof_map[block].end();
1103 next_free_index = shifts[block];
1105 for (
typename std::vector<types::global_dof_index>::const_iterator
1106 dof_index = begin_of_component;
1107 dof_index != end_of_component; ++dof_index)
1109 Assert (start->get_dof_handler().locally_owned_dofs()
1110 .index_within_set(*dof_index)
1113 ExcInternalError());
1114 new_indices[start->get_dof_handler().locally_owned_dofs()
1115 .index_within_set(*dof_index)]
1116 = next_free_index++;
1120 return next_free_index;
1130 template <
int dim,
class iterator>
1132 compute_hierarchical_recursive (
1134 std::vector<types::global_dof_index> &new_indices,
1135 const iterator &cell,
1138 if (cell->has_children())
1141 for (
unsigned int c = 0; c < GeometryInfo<dim>::max_children_per_cell; ++c)
1142 next_free = compute_hierarchical_recursive<dim> (
1150 if (cell->is_locally_owned())
1152 const unsigned int dofs_per_cell = cell->get_fe().dofs_per_cell;
1153 std::vector<types::global_dof_index> local_dof_indices (dofs_per_cell);
1154 cell->get_dof_indices (local_dof_indices);
1156 for (
unsigned int i = 0; i < dofs_per_cell; ++i)
1158 if (locally_owned.
is_element (local_dof_indices[i]))
1195 #ifdef DEAL_II_WITH_P4EST 1198 for (
unsigned int c = 0; c < tria->
n_cells (0); ++c)
1200 const unsigned int coarse_cell_index =
1204 this_cell (tria, 0, coarse_cell_index, &dof_handler);
1206 next_free = compute_hierarchical_recursive<dim> (next_free,
1212 Assert (
false, ExcNotImplemented());
1219 for (cell = dof_handler.
begin (0); cell != dof_handler.
end (0); ++cell)
1220 next_free = compute_hierarchical_recursive<dim> (next_free,
1237 (next_free <= dof_handler.
n_dofs())),
1238 ExcRenumberingIncomplete());
1241 Assert (std::find (renumbering.begin(), renumbering.end(),
1243 == renumbering.end(),
1244 ExcInternalError());
1251 template <
typename DoFHandlerType>
1254 const std::vector<bool> &selected_dofs)
1256 std::vector<types::global_dof_index> renumbering(dof_handler.n_dofs(),
1257 DoFHandlerType::invalid_dof_index);
1260 dof_handler.renumber_dofs(renumbering);
1265 template <
typename DoFHandlerType>
1268 const std::vector<bool> &selected_dofs,
1269 const unsigned int level)
1272 ExcNotInitialized());
1274 std::vector<types::global_dof_index> renumbering(dof_handler.n_dofs(level),
1275 DoFHandlerType::invalid_dof_index);
1278 dof_handler.renumber_dofs(level, renumbering);
1283 template <
typename DoFHandlerType>
1286 const DoFHandlerType &dof_handler,
1287 const std::vector<bool> &selected_dofs)
1290 Assert (selected_dofs.size() == n_dofs,
1291 ExcDimensionMismatch (selected_dofs.size(), n_dofs));
1295 Assert (new_indices.size() == n_dofs,
1296 ExcDimensionMismatch(new_indices.size(), n_dofs));
1299 selected_dofs.end(),
1305 if (selected_dofs[i] ==
false)
1307 new_indices[i] = next_unselected;
1312 new_indices[i] = next_selected;
1315 Assert (next_unselected == n_selected_dofs, ExcInternalError());
1316 Assert (next_selected == n_dofs, ExcInternalError());
1321 template <
typename DoFHandlerType>
1324 const DoFHandlerType &dof_handler,
1325 const std::vector<bool> &selected_dofs,
1326 const unsigned int level)
1329 ExcNotInitialized());
1331 const unsigned int n_dofs = dof_handler.n_dofs(level);
1332 Assert (selected_dofs.size() == n_dofs,
1333 ExcDimensionMismatch (selected_dofs.size(), n_dofs));
1337 Assert (new_indices.size() == n_dofs,
1338 ExcDimensionMismatch(new_indices.size(), n_dofs));
1340 const unsigned int n_selected_dofs = std::count (selected_dofs.begin(),
1341 selected_dofs.end(),
1344 unsigned int next_unselected = 0;
1345 unsigned int next_selected = n_selected_dofs;
1346 for (
unsigned int i=0; i<n_dofs; ++i)
1347 if (selected_dofs[i] ==
false)
1349 new_indices[i] = next_unselected;
1354 new_indices[i] = next_selected;
1357 Assert (next_unselected == n_selected_dofs, ExcInternalError());
1358 Assert (next_selected == n_dofs, ExcInternalError());
1363 template <
typename DoFHandlerType>
1366 const std::vector<typename DoFHandlerType::active_cell_iterator> &cells)
1368 std::vector<types::global_dof_index> renumbering(dof.n_dofs());
1369 std::vector<types::global_dof_index> reverse(dof.n_dofs());
1372 dof.renumber_dofs(renumbering);
1376 template <
typename DoFHandlerType>
1379 (std::vector<types::global_dof_index> &new_indices,
1380 std::vector<types::global_dof_index> &reverse,
1381 const DoFHandlerType &dof,
1382 const typename std::vector<typename DoFHandlerType::active_cell_iterator> &cells)
1384 Assert(cells.size() == dof.get_triangulation().n_active_cells(),
1385 ExcDimensionMismatch(cells.size(),
1386 dof.get_triangulation().n_active_cells()));
1397 Assert(new_indices.size() == n_global_dofs,
1398 ExcDimensionMismatch(new_indices.size(), n_global_dofs));
1399 Assert(reverse.size() == n_global_dofs,
1400 ExcDimensionMismatch(reverse.size(), n_global_dofs));
1405 std::vector<bool> already_sorted(n_global_dofs,
false);
1406 std::vector<types::global_dof_index> cell_dofs;
1408 unsigned int global_index = 0;
1410 typename std::vector<typename DoFHandlerType::active_cell_iterator>::const_iterator cell;
1412 for (cell = cells.begin(); cell != cells.end(); ++cell)
1418 unsigned int n_cell_dofs = (*cell)->get_fe().n_dofs_per_cell();
1419 cell_dofs.resize(n_cell_dofs);
1421 (*cell)->get_active_or_mg_dof_indices(cell_dofs);
1427 std::sort(cell_dofs.begin(), cell_dofs.end());
1429 for (
unsigned int i=0; i<n_cell_dofs; ++i)
1431 if (!already_sorted[cell_dofs[i]])
1433 already_sorted[cell_dofs[i]] =
true;
1434 reverse[global_index++] = cell_dofs[i];
1438 Assert(global_index == n_global_dofs, ExcRenumberingIncomplete());
1441 new_indices[reverse[i]] = i;
1446 template <
typename DoFHandlerType>
1448 (DoFHandlerType &dof,
1449 const unsigned int level,
1450 const typename std::vector<typename DoFHandlerType::level_cell_iterator> &cells)
1453 ExcNotInitialized());
1455 std::vector<types::global_dof_index> renumbering(dof.n_dofs(level));
1456 std::vector<types::global_dof_index> reverse(dof.n_dofs(level));
1459 dof.renumber_dofs(level, renumbering);
1464 template <
typename DoFHandlerType>
1466 (std::vector<types::global_dof_index> &new_order,
1467 std::vector<types::global_dof_index> &reverse,
1468 const DoFHandlerType &dof,
1469 const unsigned int level,
1470 const typename std::vector<typename DoFHandlerType::level_cell_iterator> &cells)
1472 Assert(cells.size() == dof.get_triangulation().n_cells(level),
1473 ExcDimensionMismatch(cells.size(),
1474 dof.get_triangulation().n_cells(level)));
1475 Assert (new_order.size() == dof.n_dofs(level),
1476 ExcDimensionMismatch(new_order.size(), dof.n_dofs(level)));
1477 Assert (reverse.size() == dof.n_dofs(level),
1478 ExcDimensionMismatch(reverse.size(), dof.n_dofs(level)));
1480 unsigned int n_global_dofs = dof.n_dofs(level);
1481 unsigned int n_cell_dofs = dof.get_fe().n_dofs_per_cell();
1483 std::vector<bool> already_sorted(n_global_dofs,
false);
1484 std::vector<types::global_dof_index> cell_dofs(n_cell_dofs);
1486 unsigned int global_index = 0;
1488 typename std::vector<typename DoFHandlerType::level_cell_iterator>::const_iterator cell;
1490 for (cell = cells.begin(); cell != cells.end(); ++cell)
1492 Assert ((*cell)->level() == (int) level, ExcInternalError());
1494 (*cell)->get_active_or_mg_dof_indices(cell_dofs);
1495 std::sort(cell_dofs.begin(), cell_dofs.end());
1497 for (
unsigned int i=0; i<n_cell_dofs; ++i)
1499 if (!already_sorted[cell_dofs[i]])
1501 already_sorted[cell_dofs[i]] =
true;
1502 reverse[global_index++] = cell_dofs[i];
1506 Assert(global_index == n_global_dofs, ExcRenumberingIncomplete());
1509 new_order[reverse[i]] = i;
1518 template <
typename DoFHandlerType>
1521 (std::vector<types::global_dof_index> &new_indices,
1522 std::vector<types::global_dof_index> &reverse,
1523 const DoFHandlerType &dof,
1525 const bool dof_wise_renumbering)
1527 if (dof_wise_renumbering ==
false)
1529 std::vector<typename DoFHandlerType::active_cell_iterator> ordered_cells;
1530 ordered_cells.reserve(dof.get_triangulation().n_active_cells());
1532 DoFHandlerType::space_dimension> comparator(direction);
1534 typename DoFHandlerType::active_cell_iterator p = dof.begin_active();
1535 typename DoFHandlerType::active_cell_iterator end = dof.end();
1539 ordered_cells.push_back(p);
1542 std::sort (ordered_cells.begin(), ordered_cells.end(), comparator);
1554 const unsigned int n_dofs = dof.n_dofs();
1555 std::vector<std::pair<Point<DoFHandlerType::space_dimension>,
unsigned int> > support_point_list
1559 Assert (fe_collection[0].has_support_points(),
1562 for (
unsigned int comp=0; comp<fe_collection.size(); ++comp)
1564 Assert (fe_collection[comp].has_support_points(),
1568 get_unit_support_points()));
1571 hp_fe_values (fe_collection, quadrature_collection,
1574 std::vector<bool> already_touched (n_dofs,
false);
1576 std::vector<types::global_dof_index> local_dof_indices;
1577 typename DoFHandlerType::active_cell_iterator begin = dof.begin_active();
1578 typename DoFHandlerType::active_cell_iterator end = dof.end();
1579 for ( ; begin != end; ++begin)
1581 const unsigned int dofs_per_cell = begin->get_fe().dofs_per_cell;
1582 local_dof_indices.resize (dofs_per_cell);
1583 hp_fe_values.
reinit (begin);
1586 begin->get_active_or_mg_dof_indices(local_dof_indices);
1587 const std::vector<Point<DoFHandlerType::space_dimension> > &points
1589 for (
unsigned int i=0; i<dofs_per_cell; ++i)
1590 if (!already_touched[local_dof_indices[i]])
1592 support_point_list[local_dof_indices[i]].first = points[i];
1593 support_point_list[local_dof_indices[i]].second =
1594 local_dof_indices[i];
1595 already_touched[local_dof_indices[i]] =
true;
1600 std::sort (support_point_list.begin(), support_point_list.end(),
1603 new_indices[support_point_list[i].second] = i;
1609 template <
typename DoFHandlerType>
1611 const unsigned int level,
1613 const bool dof_wise_renumbering)
1615 std::vector<types::global_dof_index> renumbering(dof.n_dofs(level));
1616 std::vector<types::global_dof_index> reverse(dof.n_dofs(level));
1618 dof_wise_renumbering);
1620 dof.renumber_dofs(level, renumbering);
1625 template <
typename DoFHandlerType>
1628 (std::vector<types::global_dof_index> &new_indices,
1629 std::vector<types::global_dof_index> &reverse,
1630 const DoFHandlerType &dof,
1631 const unsigned int level,
1633 const bool dof_wise_renumbering)
1635 if (dof_wise_renumbering ==
false)
1637 std::vector<typename DoFHandlerType::level_cell_iterator> ordered_cells;
1638 ordered_cells.reserve (dof.get_triangulation().n_cells(level));
1640 DoFHandlerType::space_dimension> comparator(direction);
1642 typename DoFHandlerType::level_cell_iterator p = dof.begin(level);
1643 typename DoFHandlerType::level_cell_iterator end = dof.end(level);
1647 ordered_cells.push_back(p);
1650 std::sort (ordered_cells.begin(), ordered_cells.end(), comparator);
1656 Assert (dof.get_fe().has_support_points(),
1658 const unsigned int n_dofs = dof.n_dofs(level);
1659 std::vector<std::pair<Point<DoFHandlerType::space_dimension>,
unsigned int> > support_point_list
1666 std::vector<bool> already_touched (dof.n_dofs(),
false);
1668 const unsigned int dofs_per_cell = dof.
get_fe().dofs_per_cell;
1669 std::vector<types::global_dof_index> local_dof_indices (dofs_per_cell);
1670 typename DoFHandlerType::level_cell_iterator begin = dof.begin(level);
1671 typename DoFHandlerType::level_cell_iterator end = dof.end(level);
1672 for ( ; begin != end; ++begin)
1675 DoFHandlerType::space_dimension>::cell_iterator &begin_tria = begin;
1676 begin->get_active_or_mg_dof_indices(local_dof_indices);
1677 fe_values.reinit (begin_tria);
1678 const std::vector<Point<DoFHandlerType::space_dimension> > &points
1679 = fe_values.get_quadrature_points ();
1680 for (
unsigned int i=0; i<dofs_per_cell; ++i)
1681 if (!already_touched[local_dof_indices[i]])
1683 support_point_list[local_dof_indices[i]].first = points[i];
1684 support_point_list[local_dof_indices[i]].second =
1685 local_dof_indices[i];
1686 already_touched[local_dof_indices[i]] =
true;
1691 std::sort (support_point_list.begin(), support_point_list.end(),
1694 new_indices[support_point_list[i].second] = i;
1720 ClockCells (
const Point<dim> ¢er,
bool counter) :
1728 template <
class DHCellIterator>
1729 bool operator () (
const DHCellIterator &c1,
1730 const DHCellIterator &c2)
const 1741 template <
class DHCellIterator,
int xdim>
1742 bool compare (
const DHCellIterator &c1,
1743 const DHCellIterator &c2,
1748 const double s1 = std::atan2(v1[0], v1[1]);
1749 const double s2 = std::atan2(v2[0], v2[1]);
1750 return ( counter ? (s1>s2) : (s2>s1));
1758 template <
class DHCellIterator>
1759 bool compare (
const DHCellIterator &,
1760 const DHCellIterator &,
1764 ExcMessage (
"This operation only makes sense for dim>=2."));
1773 template <
typename DoFHandlerType>
1776 DoFHandlerType &dof,
1780 std::vector<types::global_dof_index> renumbering(dof.n_dofs());
1783 dof.renumber_dofs(renumbering);
1788 template <
typename DoFHandlerType>
1791 (std::vector<types::global_dof_index> &new_indices,
1792 const DoFHandlerType &dof,
1796 std::vector<typename DoFHandlerType::active_cell_iterator> ordered_cells;
1797 ordered_cells.reserve (dof.get_triangulation().n_active_cells());
1798 internal::ClockCells<DoFHandlerType::space_dimension> comparator(center, counter);
1800 typename DoFHandlerType::active_cell_iterator p = dof.begin_active();
1801 typename DoFHandlerType::active_cell_iterator end = dof.end();
1805 ordered_cells.push_back(p);
1808 std::sort (ordered_cells.begin(), ordered_cells.end(), comparator);
1810 std::vector<types::global_dof_index> reverse(new_indices.size());
1816 template <
typename DoFHandlerType>
1818 const unsigned int level,
1822 std::vector<typename DoFHandlerType::level_cell_iterator> ordered_cells;
1823 ordered_cells.reserve(dof.get_triangulation().n_active_cells());
1824 internal::ClockCells<DoFHandlerType::space_dimension> comparator(center, counter);
1826 typename DoFHandlerType::level_cell_iterator p = dof.begin(level);
1827 typename DoFHandlerType::level_cell_iterator end = dof.end(level);
1831 ordered_cells.push_back(p);
1834 std::sort (ordered_cells.begin(), ordered_cells.end(), comparator);
1841 template <
typename DoFHandlerType>
1845 std::vector<types::global_dof_index> renumbering(dof_handler.n_dofs(),
1846 DoFHandlerType::invalid_dof_index);
1849 dof_handler.renumber_dofs(renumbering);
1854 template <
typename DoFHandlerType>
1857 std::vector<types::global_dof_index> &new_indices,
1858 const DoFHandlerType &dof_handler)
1861 Assert(new_indices.size() == n_dofs,
1862 ExcDimensionMismatch(new_indices.size(), n_dofs));
1864 for (
unsigned int i=0; i<n_dofs; ++i)
1870 ::boost::mt19937 random_number_generator;
1871 for (
unsigned int i=1; i<n_dofs; ++i)
1874 const unsigned int j
1875 = ::boost::random::uniform_int_distribution<>(0, i)(random_number_generator);
1879 std::swap (new_indices[i], new_indices[j]);
1885 template <
typename DoFHandlerType>
1889 std::vector<types::global_dof_index> renumbering(dof_handler.n_dofs(),
1890 DoFHandlerType::invalid_dof_index);
1893 dof_handler.renumber_dofs(renumbering);
1898 template <
typename DoFHandlerType>
1901 const DoFHandlerType &dof_handler)
1904 Assert (new_dof_indices.size() == n_dofs,
1905 ExcDimensionMismatch (new_dof_indices.size(), n_dofs));
1910 std::vector<types::subdomain_id> subdomain_association (n_dofs);
1912 subdomain_association);
1913 const unsigned int n_subdomains
1914 = *std::max_element (subdomain_association.begin(),
1915 subdomain_association.end()) + 1;
1924 std::fill (new_dof_indices.begin(), new_dof_indices.end(),
1929 if (subdomain_association[i] == subdomain)
1932 ExcInternalError());
1933 new_dof_indices[i] = next_free_index;
1938 Assert (next_free_index == n_dofs, ExcInternalError());
1939 Assert (std::find (new_dof_indices.begin(), new_dof_indices.end(),
1941 == new_dof_indices.end(),
1942 ExcInternalError());
1950 #include "dof_renumbering.inst" 1953 DEAL_II_NAMESPACE_CLOSE
types::global_dof_index size_type
#define AssertDimension(dim1, dim2)
cell_iterator begin(const unsigned int level=0) const
void minimum_degree(DoFHandlerType &dof_handler, const bool reversed_numbering=false, const bool use_constraints=false)
void renumber_dofs(const std::vector< types::global_dof_index > &new_numbers)
void compute_cell_wise(std::vector< types::global_dof_index > &renumbering, std::vector< types::global_dof_index > &inverse_renumbering, const DoFHandlerType &dof_handler, const std::vector< typename DoFHandlerType::active_cell_iterator > &cell_order)
unsigned int n_cells() const
size_type nth_index_in_set(const unsigned int local_index) const
void compute_king_ordering(std::vector< types::global_dof_index > &new_dof_indices, const DoFHandlerType &, const bool reversed_numbering=false, const bool use_constraints=false)
void sort_selected_dofs_back(DoFHandlerType &dof_handler, const std::vector< bool > &selected_dofs)
::ExceptionBase & ExcMessage(std::string arg1)
void hierarchical(DoFHandler< dim > &dof_handler)
cell_iterator end() const
void component_wise(DoFHandler< dim, spacedim > &dof_handler, const std::vector< unsigned int > &target_component=std::vector< unsigned int >())
active_cell_iterator begin_active(const unsigned int level=0) const
const FiniteElement< dim, spacedim > & get_fe() const
ActiveSelector::active_cell_iterator active_cell_iterator
Transformed quadrature points.
const std::vector< types::global_dof_index > & get_p4est_tree_to_coarse_cell_permutation() const
std::string to_string(const number value, const unsigned int digits=numbers::invalid_unsigned_int)
ActiveSelector::active_cell_iterator active_cell_iterator
const ::FEValues< dim, spacedim > & get_present_fe_values() const
active_cell_iterator begin_active(const unsigned int level=0) const
const std::vector< Point< spacedim > > & get_quadrature_points() const
unsigned int n_locally_owned_dofs() const
void reinit(const TriaIterator< DoFCellAccessor< DoFHandlerType, lda > > cell, const unsigned int q_index=numbers::invalid_unsigned_int, const unsigned int mapping_index=numbers::invalid_unsigned_int, const unsigned int fe_index=numbers::invalid_unsigned_int)
void make_hanging_node_constraints(const DoFHandlerType &dof_handler, ConstraintMatrix &constraints)
void random(DoFHandlerType &dof_handler)
void compute_minimum_degree(std::vector< types::global_dof_index > &new_dof_indices, const DoFHandlerType &, const bool reversed_numbering=false, const bool use_constraints=false)
void Cuthill_McKee(DoFHandlerType &dof_handler, const bool reversed_numbering=false, const bool use_constraints=false)
unsigned int global_dof_index
#define Assert(cond, exc)
void compute_subdomain_wise(std::vector< types::global_dof_index > &new_dof_indices, const DoFHandlerType &dof_handler)
bool is_primitive(const unsigned int i) const
size_type index_within_set(const size_type global_index) const
const ComponentMask & get_nonzero_components(const unsigned int i) const
types::global_dof_index n_dofs() const
void compute_random(std::vector< types::global_dof_index > &new_dof_indices, const DoFHandlerType &dof_handler)
unsigned int subdomain_id
void downstream(DoFHandlerType &dof_handler, const Point< DoFHandlerType::space_dimension > &direction, const bool dof_wise_renumbering=false)
unsigned int n_mpi_processes(const MPI_Comm &mpi_communicator)
void compute_sort_selected_dofs_back(std::vector< types::global_dof_index > &new_dof_indices, const DoFHandlerType &dof_handler, const std::vector< bool > &selected_dofs)
const unsigned int dofs_per_cell
void renumber_dofs(const std::vector< types::global_dof_index > &new_numbers)
std::pair< unsigned int, unsigned int > system_to_component_index(const unsigned int index) const
void make_sparsity_pattern(const DoFHandlerType &dof_handler, SparsityPatternType &sparsity_pattern, const ConstraintMatrix &constraints=ConstraintMatrix(), const bool keep_constrained_dofs=true, const types::subdomain_id subdomain_id=numbers::invalid_subdomain_id)
void compute_clockwise_dg(std::vector< types::global_dof_index > &new_dof_indices, const DoFHandlerType &dof_handler, const Point< DoFHandlerType::space_dimension > ¢er, const bool counter)
void king_ordering(DoFHandlerType &dof_handler, const bool reversed_numbering=false, const bool use_constraints=false)
std::pair< unsigned int, types::global_dof_index > system_to_block_index(const unsigned int component) const
void block_wise(DoFHandler< dim, spacedim > &dof_handler)
unsigned int first_selected_component(const unsigned int overall_number_of_components=numbers::invalid_unsigned_int) const
types::global_dof_index compute_component_wise(std::vector< types::global_dof_index > &new_dof_indices, const ITERATOR &start, const ENDITERATOR &end, const std::vector< unsigned int > &target_component, bool is_level_operation)
void compute_Cuthill_McKee(std::vector< types::global_dof_index > &new_dof_indices, const DoFHandlerType &, const bool reversed_numbering=false, const bool use_constraints=false)
types::global_dof_index n_dofs() const
std::vector< unsigned int > reverse_permutation(const std::vector< unsigned int > &permutation)
const Triangulation< dim, spacedim > & get_triangulation() const
bool is_element(const size_type index) const
void subdomain_wise(DoFHandlerType &dof_handler)
void clockwise_dg(DoFHandlerType &dof_handler, const Point< DoFHandlerType::space_dimension > ¢er, const bool counter=false)
const types::global_dof_index invalid_dof_index
const IndexSet & locally_owned_dofs() const
void compute_downstream(std::vector< types::global_dof_index > &new_dof_indices, std::vector< types::global_dof_index > &reverse, const DoFHandlerType &dof_handler, const Point< DoFHandlerType::space_dimension > &direction, const bool dof_wise_renumbering)
types::global_dof_index compute_block_wise(std::vector< types::global_dof_index > &new_dof_indices, const ITERATOR &start, const ENDITERATOR &end, bool is_level_operation)
size_type n_elements() const
void push_back(const Quadrature< dim > &new_quadrature)
cell_iterator end() const
void cell_wise(DoFHandlerType &dof_handler, const std::vector< typename DoFHandlerType::active_cell_iterator > &cell_order)