libMesh::SparsityPattern::Build Class Reference

#include <sparsity_pattern.h>

Inheritance diagram for libMesh::SparsityPattern::Build:

Public Member Functions

 Build (const MeshBase &mesh_in, const DofMap &dof_map_in, const CouplingMatrix *dof_coupling_in, const bool implicit_neighbor_dofs_in, const bool need_full_sparsity_pattern_in)
 
 Build (Build &other, Threads::split)
 
void operator() (const ConstElemRange &range)
 
void join (const Build &other)
 
void parallel_sync ()
 
const Parallel::Communicatorcomm () const
 
processor_id_type n_processors () const
 
processor_id_type processor_id () const
 

Public Attributes

SparsityPattern::Graph sparsity_pattern
 
SparsityPattern::NonlocalGraph nonlocal_pattern
 
std::vector< dof_id_typen_nz
 
std::vector< dof_id_typen_oz
 

Protected Attributes

const Parallel::Communicator_communicator
 

Private Attributes

const MeshBasemesh
 
const DofMapdof_map
 
const CouplingMatrixdof_coupling
 
const bool implicit_neighbor_dofs
 
const bool need_full_sparsity_pattern
 

Detailed Description

This helper class can be called on multiple threads to compute the sparsity pattern (or graph) of the sparse matrix resulting from the discretization. This pattern may be used directly by a particular sparse matrix format (e.g. LaspackMatrix) or indirectly (e.g. PetscMatrix). In the latter case the number of nonzeros per row of the matrix is needed for efficient preallocation. In this case it suffices to provide estimate (but bounding) values, and in this case the threaded method can take some short-cuts for efficiency.

Definition at line 79 of file sparsity_pattern.h.

Constructor & Destructor Documentation

libMesh::SparsityPattern::Build::Build ( const MeshBase mesh_in,
const DofMap dof_map_in,
const CouplingMatrix dof_coupling_in,
const bool  implicit_neighbor_dofs_in,
const bool  need_full_sparsity_pattern_in 
)

Definition at line 35 of file sparsity_pattern.C.

39  :
40  ParallelObject(dof_map_in),
41  mesh(mesh_in),
42  dof_map(dof_map_in),
43  dof_coupling(dof_coupling_in),
44  implicit_neighbor_dofs(implicit_neighbor_dofs_in),
45  need_full_sparsity_pattern(need_full_sparsity_pattern_in),
48  n_nz(),
49  n_oz()
50  {}
libMesh::SparsityPattern::Build::Build ( Build other,
Threads::split   
)

Definition at line 54 of file sparsity_pattern.C.

54  :
55  ParallelObject(other),
56  mesh(other.mesh),
57  dof_map(other.dof_map),
58  dof_coupling(other.dof_coupling),
59  implicit_neighbor_dofs(other.implicit_neighbor_dofs),
60  need_full_sparsity_pattern(other.need_full_sparsity_pattern),
63  n_nz(),
64  n_oz()
65  {}

Member Function Documentation

const Parallel::Communicator& libMesh::ParallelObject::comm ( ) const
inlineinherited
Returns
a reference to the Parallel::Communicator object used by this mesh.

Definition at line 86 of file parallel_object.h.

References libMesh::ParallelObject::_communicator.

Referenced by libMesh::__libmesh_petsc_diff_solver_jacobian(), libMesh::__libmesh_petsc_diff_solver_monitor(), libMesh::__libmesh_petsc_diff_solver_residual(), libMesh::__libmesh_petsc_snes_jacobian(), libMesh::__libmesh_petsc_snes_residual(), libMesh::MeshRefinement::_coarsen_elements(), libMesh::ExactSolution::_compute_error(), libMesh::MetisPartitioner::_do_partition(), libMesh::ParmetisPartitioner::_do_repartition(), libMesh::UniformRefinementEstimator::_estimate_error(), libMesh::SlepcEigenSolver< T >::_petsc_shell_matrix_get_diagonal(), libMesh::PetscLinearSolver< T >::_petsc_shell_matrix_get_diagonal(), libMesh::SlepcEigenSolver< T >::_petsc_shell_matrix_mult(), libMesh::PetscLinearSolver< T >::_petsc_shell_matrix_mult(), libMesh::PetscLinearSolver< T >::_petsc_shell_matrix_mult_add(), libMesh::EquationSystems::_read_impl(), libMesh::MeshRefinement::_refine_elements(), libMesh::ParallelMesh::add_elem(), libMesh::ImplicitSystem::add_matrix(), libMesh::ParallelMesh::add_node(), libMesh::System::add_vector(), libMesh::UnstructuredMesh::all_second_order(), libMesh::LaplaceMeshSmoother::allgather_graph(), libMesh::FEMSystem::assemble_qoi(), libMesh::MeshCommunication::assign_global_indices(), libMesh::ParmetisPartitioner::assign_partitioning(), libMesh::DofMap::attach_matrix(), libMesh::MeshTools::bounding_box(), libMesh::System::calculate_norm(), libMesh::MeshRefinement::coarsen_elements(), libMesh::Nemesis_IO_Helper::compute_num_global_elem_blocks(), libMesh::Nemesis_IO_Helper::compute_num_global_nodesets(), libMesh::Nemesis_IO_Helper::compute_num_global_sidesets(), libMesh::Problem_Interface::computeF(), libMesh::Problem_Interface::computeJacobian(), libMesh::Problem_Interface::computePreconditioner(), libMesh::MeshTools::correct_node_proc_ids(), libMesh::MeshCommunication::delete_remote_elements(), libMesh::DofMap::distribute_dofs(), DMlibMeshFunction(), DMlibMeshJacobian(), DMLibMeshSetSystem(), DMVariableBounds_libMesh(), libMesh::MeshRefinement::eliminate_unrefined_patches(), libMesh::WeightedPatchRecoveryErrorEstimator::estimate_error(), libMesh::PatchRecoveryErrorEstimator::estimate_error(), libMesh::JumpErrorEstimator::estimate_error(), libMesh::AdjointRefinementEstimator::estimate_error(), libMesh::MeshRefinement::flag_elements_by_elem_fraction(), libMesh::MeshRefinement::flag_elements_by_error_fraction(), libMesh::MeshRefinement::flag_elements_by_nelem_target(), libMesh::for(), libMesh::CondensedEigenSystem::get_eigenpair(), libMesh::ImplicitSystem::get_linear_solver(), libMesh::LocationMap< T >::init(), libMesh::PetscDiffSolver::init(), libMesh::TimeSolver::init(), libMesh::SystemSubsetBySubdomain::init(), libMesh::EigenSystem::init_data(), libMesh::EigenSystem::init_matrices(), libMesh::ParmetisPartitioner::initialize(), libMesh::MeshTools::libmesh_assert_valid_dof_ids(), libMesh::ParallelMesh::libmesh_assert_valid_parallel_flags(), libMesh::MeshTools::libmesh_assert_valid_procids< Elem >(), libMesh::MeshTools::libmesh_assert_valid_procids< Node >(), libMesh::MeshTools::libmesh_assert_valid_refinement_flags(), libMesh::MeshRefinement::limit_level_mismatch_at_edge(), libMesh::MeshRefinement::limit_level_mismatch_at_node(), libMesh::MeshRefinement::make_coarsening_compatible(), libMesh::MeshCommunication::make_elems_parallel_consistent(), libMesh::MeshRefinement::make_flags_parallel_consistent(), libMesh::MeshCommunication::make_node_ids_parallel_consistent(), libMesh::MeshCommunication::make_node_proc_ids_parallel_consistent(), libMesh::MeshCommunication::make_nodes_parallel_consistent(), libMesh::MeshRefinement::make_refinement_compatible(), libMesh::FEMSystem::mesh_position_set(), libMesh::MeshSerializer::MeshSerializer(), libMesh::ParallelMesh::n_active_elem(), libMesh::MeshTools::n_active_levels(), libMesh::BoundaryInfo::n_boundary_conds(), libMesh::BoundaryInfo::n_edge_conds(), libMesh::CondensedEigenSystem::n_global_non_condensed_dofs(), libMesh::MeshTools::n_levels(), libMesh::BoundaryInfo::n_nodeset_conds(), libMesh::MeshTools::n_p_levels(), libMesh::ParallelMesh::parallel_max_elem_id(), libMesh::ParallelMesh::parallel_max_node_id(), libMesh::ParallelMesh::parallel_n_elem(), libMesh::ParallelMesh::parallel_n_nodes(), libMesh::Partitioner::partition(), libMesh::Partitioner::partition_unpartitioned_elements(), libMesh::System::point_gradient(), libMesh::System::point_hessian(), libMesh::System::point_value(), libMesh::MeshBase::prepare_for_use(), libMesh::System::project_vector(), libMesh::Nemesis_IO::read(), libMesh::XdrIO::read(), libMesh::System::read_header(), libMesh::System::read_legacy_data(), libMesh::System::read_SCALAR_dofs(), libMesh::XdrIO::read_serialized_bc_names(), libMesh::XdrIO::read_serialized_bcs(), libMesh::System::read_serialized_blocked_dof_objects(), libMesh::XdrIO::read_serialized_connectivity(), libMesh::XdrIO::read_serialized_nodes(), libMesh::XdrIO::read_serialized_nodesets(), libMesh::XdrIO::read_serialized_subdomain_names(), libMesh::System::read_serialized_vector(), libMesh::MeshBase::recalculate_n_partitions(), libMesh::MeshRefinement::refine_and_coarsen_elements(), libMesh::MeshRefinement::refine_elements(), libMesh::Partitioner::set_node_processor_ids(), libMesh::DofMap::set_nonlocal_dof_objects(), libMesh::LaplaceMeshSmoother::smooth(), libMesh::MeshBase::subdomain_ids(), libMesh::BoundaryInfo::sync(), libMesh::Parallel::sync_element_data_by_parent_id(), libMesh::MeshRefinement::test_level_one(), libMesh::MeshRefinement::test_unflagged(), libMesh::MeshTools::total_weight(), libMesh::CheckpointIO::write(), libMesh::XdrIO::write(), libMesh::UnstructuredMesh::write(), libMesh::LegacyXdrIO::write_mesh(), libMesh::System::write_SCALAR_dofs(), libMesh::XdrIO::write_serialized_bcs(), libMesh::System::write_serialized_blocked_dof_objects(), libMesh::XdrIO::write_serialized_connectivity(), libMesh::XdrIO::write_serialized_nodes(), libMesh::XdrIO::write_serialized_nodesets(), and libMesh::DivaIO::write_stream().

87  { return _communicator; }
void libMesh::SparsityPattern::Build::join ( const Build other)

Definition at line 2593 of file dof_map.C.

References dof_id, libMesh::dof_map, libMesh::DofMap::end_dof(), libMesh::DofMap::first_dof(), libMesh::libmesh_assert(), std::min(), libMesh::DofMap::n_dofs(), libMesh::DofMap::n_dofs_on_processor(), n_nz, n_oz, nonlocal_pattern, libMesh::processor_id(), libMesh::ParallelObject::processor_id(), and sparsity_pattern.

2594 {
2595  const processor_id_type proc_id = mesh.processor_id();
2596  const dof_id_type n_global_dofs = dof_map.n_dofs();
2597  const dof_id_type n_dofs_on_proc = dof_map.n_dofs_on_processor(proc_id);
2598  const dof_id_type first_dof_on_proc = dof_map.first_dof(proc_id);
2599  const dof_id_type end_dof_on_proc = dof_map.end_dof(proc_id);
2600 
2601  libmesh_assert_equal_to (sparsity_pattern.size(), other.sparsity_pattern.size());
2602  libmesh_assert_equal_to (n_nz.size(), sparsity_pattern.size());
2603  libmesh_assert_equal_to (n_oz.size(), sparsity_pattern.size());
2604 
2605  for (dof_id_type r=0; r<n_dofs_on_proc; r++)
2606  {
2607  // increment the number of on and off-processor nonzeros in this row
2608  // (note this will be an upper bound unless we need the full sparsity pattern)
2610  {
2612  const SparsityPattern::Row &their_row = other.sparsity_pattern[r];
2613 
2614  // simple copy if I have no dofs
2615  if (my_row.empty())
2616  my_row = their_row;
2617 
2618  // otherwise add their DOFs to mine, resort, and re-unique the row
2619  else if (!their_row.empty()) // do nothing for the trivial case where
2620  { // their row is empty
2621  my_row.insert (my_row.end(),
2622  their_row.begin(),
2623  their_row.end());
2624 
2625  // We cannot use SparsityPattern::sort_row() here because it expects
2626  // the [begin,middle) [middle,end) to be non-overlapping. This is not
2627  // necessarily the case here, so use std::sort()
2628  std::sort (my_row.begin(), my_row.end());
2629 
2630  my_row.erase(std::unique (my_row.begin(), my_row.end()), my_row.end());
2631  }
2632 
2633  // fix the number of on and off-processor nonzeros in this row
2634  n_nz[r] = n_oz[r] = 0;
2635 
2636  for (std::size_t j=0; j<my_row.size(); j++)
2637  if ((my_row[j] < first_dof_on_proc) || (my_row[j] >= end_dof_on_proc))
2638  n_oz[r]++;
2639  else
2640  n_nz[r]++;
2641  }
2642  else
2643  {
2644  n_nz[r] += other.n_nz[r];
2645  n_nz[r] = std::min(n_nz[r], n_dofs_on_proc);
2646  n_oz[r] += other.n_oz[r];
2647  n_oz[r] =std::min(n_oz[r], static_cast<dof_id_type>(n_global_dofs-n_nz[r]));
2648  }
2649  }
2650 
2651  // Move nonlocal row information to ourselves; the other thread
2652  // won't need it in the map after that.
2653  NonlocalGraph::const_iterator it = other.nonlocal_pattern.begin();
2654  for (; it != other.nonlocal_pattern.end(); ++it)
2655  {
2656  const dof_id_type dof_id = it->first;
2657 
2658 #ifndef NDEBUG
2659  processor_id_type dbg_proc_id = 0;
2660  while (dof_id >= dof_map.end_dof(dbg_proc_id))
2661  dbg_proc_id++;
2662  libmesh_assert (dbg_proc_id != this->processor_id());
2663 #endif
2664 
2665  const SparsityPattern::Row &their_row = it->second;
2666 
2667  // We should have no empty values in a map
2668  libmesh_assert (!their_row.empty());
2669 
2670  NonlocalGraph::iterator my_it = nonlocal_pattern.find(it->first);
2671  if (my_it == nonlocal_pattern.end())
2672  {
2673 // nonlocal_pattern[it->first].swap(their_row);
2674  nonlocal_pattern[it->first] = their_row;
2675  }
2676  else
2677  {
2678  SparsityPattern::Row &my_row = my_it->second;
2679 
2680  my_row.insert (my_row.end(),
2681  their_row.begin(),
2682  their_row.end());
2683 
2684  // We cannot use SparsityPattern::sort_row() here because it expects
2685  // the [begin,middle) [middle,end) to be non-overlapping. This is not
2686  // necessarily the case here, so use std::sort()
2687  std::sort (my_row.begin(), my_row.end());
2688 
2689  my_row.erase(std::unique (my_row.begin(), my_row.end()), my_row.end());
2690  }
2691  }
2692 }
processor_id_type libMesh::ParallelObject::n_processors ( ) const
inlineinherited
Returns
the number of processors in the group.

Definition at line 92 of file parallel_object.h.

References libMesh::ParallelObject::_communicator, and libMesh::Parallel::Communicator::size().

Referenced by libMesh::ParmetisPartitioner::_do_repartition(), libMesh::ParallelMesh::add_elem(), libMesh::ParallelMesh::add_node(), libMesh::LaplaceMeshSmoother::allgather_graph(), libMesh::ParmetisPartitioner::assign_partitioning(), libMesh::ParallelMesh::assign_unique_ids(), libMesh::AztecLinearSolver< T >::AztecLinearSolver(), libMesh::ParallelMesh::clear(), libMesh::Nemesis_IO_Helper::compute_border_node_ids(), libMesh::Nemesis_IO_Helper::construct_nemesis_filename(), libMesh::UnstructuredMesh::create_pid_mesh(), libMesh::DofMap::distribute_dofs(), libMesh::DofMap::distribute_local_dofs_node_major(), libMesh::DofMap::distribute_local_dofs_var_major(), libMesh::EnsightIO::EnsightIO(), libMesh::MeshBase::get_info(), libMesh::EquationSystems::init(), libMesh::SystemSubsetBySubdomain::init(), libMesh::ParmetisPartitioner::initialize(), libMesh::Nemesis_IO_Helper::initialize(), libMesh::MeshTools::libmesh_assert_valid_dof_ids(), libMesh::MeshTools::libmesh_assert_valid_procids< Elem >(), libMesh::MeshTools::libmesh_assert_valid_procids< Node >(), libMesh::MeshTools::libmesh_assert_valid_refinement_flags(), libMesh::MeshBase::n_active_elem_on_proc(), libMesh::MeshBase::n_elem_on_proc(), libMesh::MeshBase::n_nodes_on_proc(), libMesh::Partitioner::partition(), libMesh::MeshBase::partition(), libMesh::Partitioner::partition_unpartitioned_elements(), libMesh::PetscLinearSolver< T >::PetscLinearSolver(), libMesh::System::point_gradient(), libMesh::System::point_hessian(), libMesh::System::point_value(), libMesh::MeshTools::processor_bounding_box(), libMesh::System::project_vector(), libMesh::Nemesis_IO::read(), libMesh::CheckpointIO::read(), libMesh::UnstructuredMesh::read(), libMesh::System::read_parallel_data(), libMesh::System::read_SCALAR_dofs(), libMesh::System::read_serialized_blocked_dof_objects(), libMesh::System::read_serialized_vector(), libMesh::Partitioner::repartition(), libMesh::Partitioner::set_node_processor_ids(), libMesh::DofMap::set_nonlocal_dof_objects(), libMesh::BoundaryInfo::sync(), libMesh::ParallelMesh::update_parallel_id_counts(), libMesh::CheckpointIO::write(), libMesh::GMVIO::write_binary(), libMesh::GMVIO::write_discontinuous_gmv(), libMesh::System::write_parallel_data(), libMesh::System::write_SCALAR_dofs(), libMesh::XdrIO::write_serialized_bcs(), libMesh::System::write_serialized_blocked_dof_objects(), libMesh::XdrIO::write_serialized_connectivity(), libMesh::XdrIO::write_serialized_nodes(), and libMesh::XdrIO::write_serialized_nodesets().

93  { return libmesh_cast_int<processor_id_type>(_communicator.size()); }
void libMesh::SparsityPattern::Build::operator() ( const ConstElemRange range)

Definition at line 2205 of file dof_map.C.

References libMesh::Elem::active_family_tree_by_neighbor(), libMesh::StoredRange< iterator_type, object_type >::begin(), dof_coupling, libMesh::DofMap::dof_indices(), dof_map, libMesh::CouplingMatrix::empty(), libMesh::StoredRange< iterator_type, object_type >::end(), libMesh::DofMap::end_dof(), libMesh::DofMap::find_connected_dofs(), libMesh::DofMap::first_dof(), implicit_neighbor_dofs, libMesh::libmesh_assert(), libMesh::DofMap::n_dofs_on_processor(), n_nz, n_oz, libMesh::Elem::n_sides(), libMesh::DofMap::n_variables(), need_full_sparsity_pattern, libMesh::Elem::neighbor(), nonlocal_pattern, libMesh::ParallelObject::processor_id(), libMesh::CouplingMatrix::size(), libMesh::SparsityPattern::sort_row(), and sparsity_pattern.

2206 {
2207  // Compute the sparsity structure of the global matrix. This can be
2208  // fed into a PetscMatrix to allocate exacly the number of nonzeros
2209  // necessary to store the matrix. This algorithm should be linear
2210  // in the (# of elements)*(# nodes per element)
2211  const processor_id_type proc_id = mesh.processor_id();
2212  const dof_id_type n_dofs_on_proc = dof_map.n_dofs_on_processor(proc_id);
2213  const dof_id_type first_dof_on_proc = dof_map.first_dof(proc_id);
2214  const dof_id_type end_dof_on_proc = dof_map.end_dof(proc_id);
2215 
2216  sparsity_pattern.resize(n_dofs_on_proc);
2217 
2218  // If the user did not explicitly specify the DOF coupling
2219  // then all the DOFS are coupled to each other. Furthermore,
2220  // we can take a shortcut and do this more quickly here. So
2221  // we use an if-test.
2222  if ((dof_coupling == NULL) || (dof_coupling->empty()))
2223  {
2224  std::vector<dof_id_type>
2225  element_dofs,
2226  neighbor_dofs,
2227  dofs_to_add;
2228 
2229  std::vector<const Elem*> active_neighbors;
2230 
2231  for (ConstElemRange::const_iterator elem_it = range.begin() ; elem_it != range.end(); ++elem_it)
2232  {
2233  const Elem* const elem = *elem_it;
2234 
2235  // Get the global indices of the DOFs with support on this element
2236  dof_map.dof_indices (elem, element_dofs);
2237 #ifdef LIBMESH_ENABLE_CONSTRAINTS
2238  dof_map.find_connected_dofs (element_dofs);
2239 #endif
2240 
2241  // We can be more efficient if we sort the element DOFs
2242  // into increasing order
2243  std::sort(element_dofs.begin(), element_dofs.end());
2244 
2245  const unsigned int n_dofs_on_element =
2246  libmesh_cast_int<unsigned int>(element_dofs.size());
2247 
2248  for (unsigned int i=0; i<n_dofs_on_element; i++)
2249  {
2250  const dof_id_type ig = element_dofs[i];
2251 
2252  SparsityPattern::Row *row;
2253 
2254  // We save non-local row components for now so we can
2255  // communicate them to other processors later.
2256 
2257  if ((ig >= first_dof_on_proc) &&
2258  (ig < end_dof_on_proc))
2259  {
2260  // This is what I mean
2261  // libmesh_assert_greater_equal ((ig - first_dof_on_proc), 0);
2262  // but do the test like this because ig and
2263  // first_dof_on_proc are unsigned ints
2264  libmesh_assert_greater_equal (ig, first_dof_on_proc);
2265  libmesh_assert_less ((ig - first_dof_on_proc), sparsity_pattern.size());
2266 
2267  row = &sparsity_pattern[ig - first_dof_on_proc];
2268  }
2269  else
2270  {
2271  row = &nonlocal_pattern[ig];
2272  }
2273 
2274  // If the row is empty we will add *all* the element DOFs,
2275  // so just do that.
2276  if (row->empty())
2277  {
2278  row->insert(row->end(),
2279  element_dofs.begin(),
2280  element_dofs.end());
2281  }
2282  else
2283  {
2284  // Build a list of the DOF indices not found in the
2285  // sparsity pattern
2286  dofs_to_add.clear();
2287 
2288  // Cache iterators. Low will move forward, subsequent
2289  // searches will be on smaller ranges
2290  SparsityPattern::Row::iterator
2291  low = std::lower_bound (row->begin(), row->end(), element_dofs.front()),
2292  high = std::upper_bound (low, row->end(), element_dofs.back());
2293 
2294  for (unsigned int j=0; j<n_dofs_on_element; j++)
2295  {
2296  const dof_id_type jg = element_dofs[j];
2297 
2298  // See if jg is in the sorted range
2299  std::pair<SparsityPattern::Row::iterator,
2300  SparsityPattern::Row::iterator>
2301  pos = std::equal_range (low, high, jg);
2302 
2303  // Must add jg if it wasn't found
2304  if (pos.first == pos.second)
2305  dofs_to_add.push_back(jg);
2306 
2307  // pos.first is now a valid lower bound for any
2308  // remaining element DOFs. (That's why we sorted them.)
2309  // Use it for the next search
2310  low = pos.first;
2311  }
2312 
2313  // Add to the sparsity pattern
2314  if (!dofs_to_add.empty())
2315  {
2316  const std::size_t old_size = row->size();
2317 
2318  row->insert (row->end(),
2319  dofs_to_add.begin(),
2320  dofs_to_add.end());
2321 
2323  (row->begin(), row->begin()+old_size, row->end());
2324  }
2325  }
2326 
2327  // Now (possibly) add dofs from neighboring elements
2328  // TODO:[BSK] optimize this like above!
2330  for (unsigned int s=0; s<elem->n_sides(); s++)
2331  if (elem->neighbor(s) != NULL)
2332  {
2333  const Elem* const neighbor_0 = elem->neighbor(s);
2334 #ifdef LIBMESH_ENABLE_AMR
2335  neighbor_0->active_family_tree_by_neighbor(active_neighbors,elem);
2336 #else
2337  active_neighbors.clear();
2338  active_neighbors.push_back(neighbor_0);
2339 #endif
2340 
2341  for (std::size_t a=0; a != active_neighbors.size(); ++a)
2342  {
2343  const Elem *neighbor = active_neighbors[a];
2344 
2345  dof_map.dof_indices (neighbor, neighbor_dofs);
2346 #ifdef LIBMESH_ENABLE_CONSTRAINTS
2347  dof_map.find_connected_dofs (neighbor_dofs);
2348 #endif
2349  const std::size_t n_dofs_on_neighbor = neighbor_dofs.size();
2350 
2351  for (std::size_t j=0; j<n_dofs_on_neighbor; j++)
2352  {
2353  const dof_id_type jg = neighbor_dofs[j];
2354 
2355  // See if jg is in the sorted range
2356  std::pair<SparsityPattern::Row::iterator,
2357  SparsityPattern::Row::iterator>
2358  pos = std::equal_range (row->begin(), row->end(), jg);
2359 
2360  // Insert jg if it wasn't found
2361  if (pos.first == pos.second)
2362  row->insert (pos.first, jg);
2363  }
2364  }
2365  }
2366  }
2367  }
2368  }
2369 
2370  // This is what we do in the case that the user has specified
2371  // explicit DOF coupling.
2372  else
2373  {
2375  libmesh_assert_equal_to (dof_coupling->size(),
2376  dof_map.n_variables());
2377 
2378  const unsigned int n_var = dof_map.n_variables();
2379 
2380  std::vector<dof_id_type>
2381  element_dofs_i,
2382  element_dofs_j,
2383  neighbor_dofs,
2384  dofs_to_add;
2385 
2386 
2387  std::vector<const Elem*> active_neighbors;
2388  for (ConstElemRange::const_iterator elem_it = range.begin() ; elem_it != range.end(); ++elem_it)
2389  for (unsigned int vi=0; vi<n_var; vi++)
2390  {
2391  const Elem* const elem = *elem_it;
2392 
2393  // Find element dofs for variable vi
2394  dof_map.dof_indices (elem, element_dofs_i, vi);
2395 #ifdef LIBMESH_ENABLE_CONSTRAINTS
2396  dof_map.find_connected_dofs (element_dofs_i);
2397 #endif
2398 
2399  // We can be more efficient if we sort the element DOFs
2400  // into increasing order
2401  std::sort(element_dofs_i.begin(), element_dofs_i.end());
2402  const unsigned int n_dofs_on_element_i =
2403  libmesh_cast_int<unsigned int>(element_dofs_i.size());
2404 
2405  for (unsigned int vj=0; vj<n_var; vj++)
2406  if ((*dof_coupling)(vi,vj)) // If vi couples to vj
2407  {
2408  // Find element dofs for variable vj, note that
2409  // if vi==vj we already have the dofs.
2410  if (vi != vj)
2411  {
2412  dof_map.dof_indices (elem, element_dofs_j, vj);
2413 #ifdef LIBMESH_ENABLE_CONSTRAINTS
2414  dof_map.find_connected_dofs (element_dofs_j);
2415 #endif
2416 
2417  // We can be more efficient if we sort the element DOFs
2418  // into increasing order
2419  std::sort (element_dofs_j.begin(), element_dofs_j.end());
2420  }
2421  else
2422  element_dofs_j = element_dofs_i;
2423 
2424  const unsigned int n_dofs_on_element_j =
2425  libmesh_cast_int<unsigned int>(element_dofs_j.size());
2426 
2427  // there might be 0 dofs for the other variable on the same element (when subdomain variables do not overlap) and that's when we do not do anything
2428  if (n_dofs_on_element_j > 0)
2429  {
2430  for (unsigned int i=0; i<n_dofs_on_element_i; i++)
2431  {
2432  const dof_id_type ig = element_dofs_i[i];
2433 
2434  SparsityPattern::Row *row;
2435 
2436  // We save non-local row components for now so we can
2437  // communicate them to other processors later.
2438 
2439  if ((ig >= first_dof_on_proc) &&
2440  (ig < end_dof_on_proc))
2441  {
2442  // This is what I mean
2443  // libmesh_assert_greater_equal ((ig - first_dof_on_proc), 0);
2444  // but do the test like this because ig and
2445  // first_dof_on_proc are unsigned ints
2446  libmesh_assert_greater_equal (ig, first_dof_on_proc);
2447  libmesh_assert_less (ig, (sparsity_pattern.size() +
2448  first_dof_on_proc));
2449 
2450  row = &sparsity_pattern[ig - first_dof_on_proc];
2451  }
2452  else
2453  {
2454  row = &nonlocal_pattern[ig];
2455  }
2456 
2457  // If the row is empty we will add *all* the element j DOFs,
2458  // so just do that.
2459  if (row->empty())
2460  {
2461  row->insert(row->end(),
2462  element_dofs_j.begin(),
2463  element_dofs_j.end());
2464  }
2465  else
2466  {
2467  // Build a list of the DOF indices not found in the
2468  // sparsity pattern
2469  dofs_to_add.clear();
2470 
2471  // Cache iterators. Low will move forward, subsequent
2472  // searches will be on smaller ranges
2473  SparsityPattern::Row::iterator
2474  low = std::lower_bound
2475  (row->begin(), row->end(), element_dofs_j.front()),
2476  high = std::upper_bound
2477  (low, row->end(), element_dofs_j.back());
2478 
2479  for (unsigned int j=0; j<n_dofs_on_element_j; j++)
2480  {
2481  const dof_id_type jg = element_dofs_j[j];
2482 
2483  // See if jg is in the sorted range
2484  std::pair<SparsityPattern::Row::iterator,
2485  SparsityPattern::Row::iterator>
2486  pos = std::equal_range (low, high, jg);
2487 
2488  // Must add jg if it wasn't found
2489  if (pos.first == pos.second)
2490  dofs_to_add.push_back(jg);
2491 
2492  // pos.first is now a valid lower bound for any
2493  // remaining element j DOFs. (That's why we sorted them.)
2494  // Use it for the next search
2495  low = pos.first;
2496  }
2497 
2498  // Add to the sparsity pattern
2499  if (!dofs_to_add.empty())
2500  {
2501  const std::size_t old_size = row->size();
2502 
2503  row->insert (row->end(),
2504  dofs_to_add.begin(),
2505  dofs_to_add.end());
2506 
2508  (row->begin(), row->begin()+old_size,
2509  row->end());
2510  }
2511  }
2512  // Now (possibly) add dofs from neighboring elements
2513  // TODO:[BSK] optimize this like above!
2515  for (unsigned int s=0; s<elem->n_sides(); s++)
2516  if (elem->neighbor(s) != NULL)
2517  {
2518  const Elem* const neighbor_0 = elem->neighbor(s);
2519 #ifdef LIBMESH_ENABLE_AMR
2520  neighbor_0->active_family_tree_by_neighbor(active_neighbors,elem);
2521 #else
2522  active_neighbors.clear();
2523  active_neighbors.push_back(neighbor_0);
2524 #endif
2525 
2526  for (std::size_t a=0; a != active_neighbors.size(); ++a)
2527  {
2528  const Elem *neighbor = active_neighbors[a];
2529 
2530  dof_map.dof_indices (neighbor, neighbor_dofs);
2531 #ifdef LIBMESH_ENABLE_CONSTRAINTS
2532  dof_map.find_connected_dofs (neighbor_dofs);
2533 #endif
2534  const unsigned int n_dofs_on_neighbor =
2535  libmesh_cast_int<unsigned int>(neighbor_dofs.size());
2536 
2537  for (unsigned int j=0; j<n_dofs_on_neighbor; j++)
2538  {
2539  const dof_id_type jg = neighbor_dofs[j];
2540 
2541  // See if jg is in the sorted range
2542  std::pair<SparsityPattern::Row::iterator,
2543  SparsityPattern::Row::iterator>
2544  pos = std::equal_range (row->begin(), row->end(), jg);
2545 
2546  // Insert jg if it wasn't found
2547  if (pos.first == pos.second)
2548  row->insert (pos.first, jg);
2549  }
2550  }
2551  }
2552  }
2553  }
2554  }
2555  }
2556  }
2557 
2558  // Now a new chunk of sparsity structure is built for all of the
2559  // DOFs connected to our rows of the matrix.
2560 
2561  // If we're building a full sparsity pattern, then we've got
2562  // complete rows to work with, so we can just count them from
2563  // scratch.
2565  {
2566  n_nz.clear();
2567  n_oz.clear();
2568  }
2569 
2570  n_nz.resize (n_dofs_on_proc, 0);
2571  n_oz.resize (n_dofs_on_proc, 0);
2572 
2573  for (dof_id_type i=0; i<n_dofs_on_proc; i++)
2574  {
2575  // Get the row of the sparsity pattern
2577 
2578  for (dof_id_type j=0; j<row.size(); j++)
2579  if ((row[j] < first_dof_on_proc) || (row[j] >= end_dof_on_proc))
2580  n_oz[i]++;
2581  else
2582  n_nz[i]++;
2583 
2584  // If we're not building a full sparsity pattern, then we want
2585  // to avoid overcounting these entries as much as possible.
2587  row.clear();
2588  }
2589 }
void libMesh::SparsityPattern::Build::parallel_sync ( )

Definition at line 2696 of file dof_map.C.

References libMesh::comm, dof_id, libMesh::dof_map, libMesh::DofMap::end_dof(), libMesh::DofMap::first_dof(), libMesh::libmesh_assert(), std::min(), libMesh::DofMap::n_dofs(), libMesh::DofMap::n_dofs_on_processor(), libMesh::n_processors(), and libMesh::processor_id().

Referenced by libMesh::DofMap::build_sparsity().

2697 {
2698  parallel_object_only();
2700 
2701  const dof_id_type n_global_dofs = dof_map.n_dofs();
2702  const dof_id_type n_dofs_on_proc = dof_map.n_dofs_on_processor(this->processor_id());
2703  const dof_id_type local_first_dof = dof_map.first_dof();
2704  const dof_id_type local_end_dof = dof_map.end_dof();
2705 
2706  // Trade sparsity rows with other processors
2707  for (processor_id_type p=1; p != this->n_processors(); ++p)
2708  {
2709  // Push to processor procup while receiving from procdown
2710  processor_id_type procup = (this->processor_id() + p) %
2711  this->n_processors();
2712  processor_id_type procdown = (this->n_processors() +
2713  this->processor_id() - p) %
2714  this->n_processors();
2715 
2716  // Pack the sparsity pattern rows to push to procup
2717  std::vector<dof_id_type> pushed_row_ids,
2718  pushed_row_ids_to_me;
2719  std::vector<std::vector<dof_id_type> > pushed_rows,
2720  pushed_rows_to_me;
2721 
2722  // Move nonlocal row information to a structure to send it from;
2723  // we don't need it in the map after that.
2724  NonlocalGraph::iterator it = nonlocal_pattern.begin();
2725  while (it != nonlocal_pattern.end())
2726  {
2727  const dof_id_type dof_id = it->first;
2728  processor_id_type proc_id = 0;
2729  while (dof_id >= dof_map.end_dof(proc_id))
2730  proc_id++;
2731 
2732  libmesh_assert (proc_id != this->processor_id());
2733 
2734  if (proc_id == procup)
2735  {
2736  pushed_row_ids.push_back(dof_id);
2737 
2738  // We can't just do the swap trick here, thanks to the
2739  // differing vector allocators?
2740  pushed_rows.push_back(std::vector<dof_id_type>());
2741  pushed_rows.back().assign
2742  (it->second.begin(), it->second.end());
2743 
2744  nonlocal_pattern.erase(it++);
2745  }
2746  else
2747  ++it;
2748  }
2749 
2750  this->comm().send_receive(procup, pushed_row_ids,
2751  procdown, pushed_row_ids_to_me);
2752  this->comm().send_receive(procup, pushed_rows,
2753  procdown, pushed_rows_to_me);
2754  pushed_row_ids.clear();
2755  pushed_rows.clear();
2756 
2757  const std::size_t n_rows = pushed_row_ids_to_me.size();
2758  for (std::size_t i=0; i != n_rows; ++i)
2759  {
2760  const dof_id_type r = pushed_row_ids_to_me[i];
2761  const dof_id_type my_r = r - local_first_dof;
2762 
2763  std::vector<dof_id_type> &their_row = pushed_rows_to_me[i];
2764 
2766  {
2767  SparsityPattern::Row &my_row =
2768  sparsity_pattern[my_r];
2769 
2770  // They wouldn't have sent an empty row
2771  libmesh_assert(!their_row.empty());
2772 
2773  // We can end up with an empty row on a dof that touches our
2774  // inactive elements but not our active ones
2775  if (my_row.empty())
2776  {
2777  my_row.assign (their_row.begin(),
2778  their_row.end());
2779  }
2780  else
2781  {
2782  my_row.insert (my_row.end(),
2783  their_row.begin(),
2784  their_row.end());
2785 
2786  // We cannot use SparsityPattern::sort_row() here because it expects
2787  // the [begin,middle) [middle,end) to be non-overlapping. This is not
2788  // necessarily the case here, so use std::sort()
2789  std::sort (my_row.begin(), my_row.end());
2790 
2791  my_row.erase(std::unique (my_row.begin(), my_row.end()), my_row.end());
2792  }
2793 
2794  // fix the number of on and off-processor nonzeros in this row
2795  n_nz[my_r] = n_oz[my_r] = 0;
2796 
2797  for (std::size_t j=0; j<my_row.size(); j++)
2798  if ((my_row[j] < local_first_dof) || (my_row[j] >= local_end_dof))
2799  n_oz[my_r]++;
2800  else
2801  n_nz[my_r]++;
2802  }
2803  else
2804  {
2805  for (std::size_t j=0; j<their_row.size(); j++)
2806  if ((their_row[j] < local_first_dof) || (their_row[j] >= local_end_dof))
2807  n_oz[my_r]++;
2808  else
2809  n_nz[my_r]++;
2810 
2811  n_nz[my_r] = std::min(n_nz[my_r], n_dofs_on_proc);
2812  n_oz[my_r] = std::min(n_oz[my_r],
2813  static_cast<dof_id_type>(n_global_dofs-n_nz[my_r]));
2814  }
2815  }
2816  }
2817 
2818  // We should have sent everything at this point.
2819  libmesh_assert (nonlocal_pattern.empty());
2820 }
processor_id_type libMesh::ParallelObject::processor_id ( ) const
inlineinherited
Returns
the rank of this processor in the group.

Definition at line 98 of file parallel_object.h.

References libMesh::ParallelObject::_communicator, and libMesh::Parallel::Communicator::rank().

Referenced by libMesh::MetisPartitioner::_do_partition(), libMesh::EquationSystems::_read_impl(), libMesh::SerialMesh::active_local_elements_begin(), libMesh::ParallelMesh::active_local_elements_begin(), libMesh::SerialMesh::active_local_elements_end(), libMesh::ParallelMesh::active_local_elements_end(), libMesh::SerialMesh::active_local_subdomain_elements_begin(), libMesh::ParallelMesh::active_local_subdomain_elements_begin(), libMesh::SerialMesh::active_local_subdomain_elements_end(), libMesh::ParallelMesh::active_local_subdomain_elements_end(), libMesh::SerialMesh::active_not_local_elements_begin(), libMesh::ParallelMesh::active_not_local_elements_begin(), libMesh::SerialMesh::active_not_local_elements_end(), libMesh::ParallelMesh::active_not_local_elements_end(), libMesh::ParallelMesh::add_elem(), libMesh::DofMap::add_neighbors_to_send_list(), libMesh::ParallelMesh::add_node(), libMesh::UnstructuredMesh::all_second_order(), libMesh::ParmetisPartitioner::assign_partitioning(), libMesh::EquationSystems::build_discontinuous_solution_vector(), libMesh::Nemesis_IO_Helper::build_element_and_node_maps(), libMesh::ParmetisPartitioner::build_graph(), libMesh::InfElemBuilder::build_inf_elem(), libMesh::DofMap::build_sparsity(), libMesh::ParallelMesh::clear(), libMesh::ExodusII_IO_Helper::close(), libMesh::Nemesis_IO_Helper::compute_border_node_ids(), libMesh::Nemesis_IO_Helper::compute_communication_map_parameters(), libMesh::Nemesis_IO_Helper::compute_internal_and_border_elems_and_internal_nodes(), libMesh::Nemesis_IO_Helper::compute_node_communication_maps(), libMesh::Nemesis_IO_Helper::compute_num_global_elem_blocks(), libMesh::Nemesis_IO_Helper::compute_num_global_nodesets(), libMesh::Nemesis_IO_Helper::compute_num_global_sidesets(), libMesh::Nemesis_IO_Helper::construct_nemesis_filename(), libMesh::ExodusII_IO_Helper::create(), libMesh::DofMap::distribute_dofs(), libMesh::DofMap::distribute_local_dofs_node_major(), libMesh::DofMap::distribute_local_dofs_var_major(), libMesh::DofMap::end_dof(), libMesh::DofMap::end_old_dof(), libMesh::EnsightIO::EnsightIO(), libMesh::UnstructuredMesh::find_neighbors(), libMesh::DofMap::first_dof(), libMesh::DofMap::first_old_dof(), libMesh::Nemesis_IO_Helper::get_cmap_params(), libMesh::Nemesis_IO_Helper::get_eb_info_global(), libMesh::Nemesis_IO_Helper::get_elem_cmap(), libMesh::Nemesis_IO_Helper::get_elem_map(), libMesh::MeshBase::get_info(), libMesh::Nemesis_IO_Helper::get_init_global(), libMesh::Nemesis_IO_Helper::get_init_info(), libMesh::Nemesis_IO_Helper::get_loadbal_param(), libMesh::Nemesis_IO_Helper::get_node_cmap(), libMesh::Nemesis_IO_Helper::get_node_map(), libMesh::Nemesis_IO_Helper::get_ns_param_global(), libMesh::Nemesis_IO_Helper::get_ss_param_global(), libMesh::MeshFunction::gradient(), libMesh::MeshFunction::hessian(), libMesh::SystemSubsetBySubdomain::init(), libMesh::ParmetisPartitioner::initialize(), libMesh::ExodusII_IO_Helper::initialize(), libMesh::ExodusII_IO_Helper::initialize_discontinuous(), libMesh::ExodusII_IO_Helper::initialize_element_variables(), libMesh::ExodusII_IO_Helper::initialize_global_variables(), libMesh::ExodusII_IO_Helper::initialize_nodal_variables(), join(), libMesh::DofMap::last_dof(), libMesh::MeshTools::libmesh_assert_valid_procids< Elem >(), libMesh::MeshTools::libmesh_assert_valid_procids< Node >(), libMesh::SerialMesh::local_elements_begin(), libMesh::ParallelMesh::local_elements_begin(), libMesh::SerialMesh::local_elements_end(), libMesh::ParallelMesh::local_elements_end(), libMesh::SerialMesh::local_level_elements_begin(), libMesh::ParallelMesh::local_level_elements_begin(), libMesh::SerialMesh::local_level_elements_end(), libMesh::ParallelMesh::local_level_elements_end(), libMesh::SerialMesh::local_nodes_begin(), libMesh::ParallelMesh::local_nodes_begin(), libMesh::SerialMesh::local_nodes_end(), libMesh::ParallelMesh::local_nodes_end(), libMesh::SerialMesh::local_not_level_elements_begin(), libMesh::ParallelMesh::local_not_level_elements_begin(), libMesh::SerialMesh::local_not_level_elements_end(), libMesh::ParallelMesh::local_not_level_elements_end(), libMesh::MeshRefinement::make_coarsening_compatible(), libMesh::MeshBase::n_active_local_elem(), libMesh::BoundaryInfo::n_boundary_conds(), libMesh::BoundaryInfo::n_edge_conds(), libMesh::DofMap::n_local_dofs(), libMesh::System::n_local_dofs(), libMesh::MeshBase::n_local_elem(), libMesh::MeshBase::n_local_nodes(), libMesh::BoundaryInfo::n_nodeset_conds(), libMesh::SerialMesh::not_local_elements_begin(), libMesh::ParallelMesh::not_local_elements_begin(), libMesh::SerialMesh::not_local_elements_end(), libMesh::ParallelMesh::not_local_elements_end(), libMesh::WeightedPatchRecoveryErrorEstimator::EstimateError::operator()(), operator()(), libMesh::PatchRecoveryErrorEstimator::EstimateError::operator()(), libMesh::MeshFunction::operator()(), libMesh::ParallelMesh::ParallelMesh(), libMesh::System::point_gradient(), libMesh::System::point_hessian(), libMesh::System::point_value(), libMesh::System::project_vector(), libMesh::Nemesis_IO_Helper::put_cmap_params(), libMesh::Nemesis_IO_Helper::put_elem_cmap(), libMesh::Nemesis_IO_Helper::put_elem_map(), libMesh::Nemesis_IO_Helper::put_loadbal_param(), libMesh::Nemesis_IO_Helper::put_node_cmap(), libMesh::Nemesis_IO_Helper::put_node_map(), libMesh::Nemesis_IO::read(), libMesh::CheckpointIO::read(), libMesh::XdrIO::read(), libMesh::UnstructuredMesh::read(), libMesh::CheckpointIO::read_connectivity(), libMesh::ExodusII_IO_Helper::read_elem_num_map(), libMesh::System::read_header(), libMesh::System::read_legacy_data(), libMesh::ExodusII_IO_Helper::read_node_num_map(), libMesh::System::read_parallel_data(), libMesh::System::read_SCALAR_dofs(), libMesh::XdrIO::read_serialized_bc_names(), libMesh::XdrIO::read_serialized_bcs(), libMesh::System::read_serialized_blocked_dof_objects(), libMesh::XdrIO::read_serialized_connectivity(), libMesh::System::read_serialized_data(), libMesh::XdrIO::read_serialized_nodes(), libMesh::XdrIO::read_serialized_nodesets(), libMesh::XdrIO::read_serialized_subdomain_names(), libMesh::System::read_serialized_vector(), libMesh::System::read_serialized_vectors(), libMesh::MeshData::read_xdr(), libMesh::Partitioner::set_node_processor_ids(), libMesh::DofMap::set_nonlocal_dof_objects(), libMesh::LaplaceMeshSmoother::smooth(), libMesh::BoundaryInfo::sync(), libMesh::MeshTools::total_weight(), libMesh::ParallelMesh::update_parallel_id_counts(), libMesh::MeshTools::weight(), libMesh::ExodusII_IO::write(), libMesh::CheckpointIO::write(), libMesh::XdrIO::write(), libMesh::UnstructuredMesh::write(), libMesh::EquationSystems::write(), libMesh::GMVIO::write_discontinuous_gmv(), libMesh::ExodusII_IO::write_element_data(), libMesh::ExodusII_IO_Helper::write_element_values(), libMesh::ExodusII_IO_Helper::write_elements(), libMesh::ExodusII_IO_Helper::write_elements_discontinuous(), libMesh::ExodusII_IO::write_global_data(), libMesh::ExodusII_IO_Helper::write_global_values(), libMesh::System::write_header(), libMesh::ExodusII_IO::write_information_records(), libMesh::ExodusII_IO_Helper::write_information_records(), libMesh::ExodusII_IO_Helper::write_nodal_coordinates(), libMesh::ExodusII_IO_Helper::write_nodal_coordinates_discontinuous(), libMesh::UCDIO::write_nodal_data(), libMesh::ExodusII_IO::write_nodal_data(), libMesh::ExodusII_IO::write_nodal_data_discontinuous(), libMesh::ExodusII_IO_Helper::write_nodal_values(), libMesh::ExodusII_IO_Helper::write_nodesets(), libMesh::Nemesis_IO_Helper::write_nodesets(), libMesh::System::write_parallel_data(), libMesh::System::write_SCALAR_dofs(), libMesh::XdrIO::write_serialized_bc_names(), libMesh::XdrIO::write_serialized_bcs(), libMesh::System::write_serialized_blocked_dof_objects(), libMesh::XdrIO::write_serialized_connectivity(), libMesh::System::write_serialized_data(), libMesh::XdrIO::write_serialized_nodes(), libMesh::XdrIO::write_serialized_nodesets(), libMesh::XdrIO::write_serialized_subdomain_names(), libMesh::System::write_serialized_vector(), libMesh::System::write_serialized_vectors(), libMesh::ExodusII_IO_Helper::write_sidesets(), libMesh::Nemesis_IO_Helper::write_sidesets(), libMesh::ExodusII_IO::write_timestep(), and libMesh::ExodusII_IO_Helper::write_timestep().

99  { return libmesh_cast_int<processor_id_type>(_communicator.rank()); }

Member Data Documentation

const CouplingMatrix* libMesh::SparsityPattern::Build::dof_coupling
private

Definition at line 84 of file sparsity_pattern.h.

Referenced by operator()().

const DofMap& libMesh::SparsityPattern::Build::dof_map
private

Definition at line 83 of file sparsity_pattern.h.

Referenced by operator()().

const bool libMesh::SparsityPattern::Build::implicit_neighbor_dofs
private

Definition at line 85 of file sparsity_pattern.h.

Referenced by operator()().

const MeshBase& libMesh::SparsityPattern::Build::mesh
private

Definition at line 82 of file sparsity_pattern.h.

std::vector<dof_id_type> libMesh::SparsityPattern::Build::n_nz
std::vector<dof_id_type> libMesh::SparsityPattern::Build::n_oz
const bool libMesh::SparsityPattern::Build::need_full_sparsity_pattern
private

Definition at line 86 of file sparsity_pattern.h.

Referenced by operator()().

SparsityPattern::NonlocalGraph libMesh::SparsityPattern::Build::nonlocal_pattern

Definition at line 91 of file sparsity_pattern.h.

Referenced by join(), and operator()().

SparsityPattern::Graph libMesh::SparsityPattern::Build::sparsity_pattern

The documentation for this class was generated from the following files:

Site Created By: libMesh Developers
Last modified: February 07 2014 16:58:02 UTC

Hosted By:
SourceForge.net Logo