libMesh::MeshRefinement Class Reference

Responsible for mesh refinement algorithms and data. More...

#include <mesh_refinement.h>

Inheritance diagram for libMesh::MeshRefinement:

Classes

class  ElementFlagging
 

Public Member Functions

 MeshRefinement (MeshBase &mesh)
 
void set_periodic_boundaries_ptr (PeriodicBoundaries *pb_ptr)
 
 ~MeshRefinement ()
 
void clear ()
 
void flag_elements_by_error_fraction (const ErrorVector &error_per_cell, const Real refine_fraction=0.3, const Real coarsen_fraction=0.0, const unsigned int max_level=libMesh::invalid_uint)
 
void flag_elements_by_error_tolerance (const ErrorVector &error_per_cell)
 
bool flag_elements_by_nelem_target (const ErrorVector &error_per_cell)
 
void flag_elements_by_elem_fraction (const ErrorVector &error_per_cell, const Real refine_fraction=0.3, const Real coarsen_fraction=0.0, const unsigned int max_level=libMesh::invalid_uint)
 
void flag_elements_by_mean_stddev (const ErrorVector &error_per_cell, const Real refine_fraction=1.0, const Real coarsen_fraction=0.0, const unsigned int max_level=libMesh::invalid_uint)
 
void flag_elements_by (ElementFlagging &element_flagging)
 
void switch_h_to_p_refinement ()
 
void add_p_to_h_refinement ()
 
bool refine_and_coarsen_elements ()
 
bool coarsen_elements ()
 
bool refine_elements ()
 
void uniformly_refine (unsigned int n=1)
 
void uniformly_coarsen (unsigned int n=1)
 
void uniformly_p_refine (unsigned int n=1)
 
void uniformly_p_coarsen (unsigned int n=1)
 
void clean_refinement_flags ()
 
bool test_level_one (bool libmesh_assert_yes=false)
 
bool test_unflagged (bool libmesh_assert_yes=false)
 
Nodeadd_node (Elem &parent, unsigned int child, unsigned int node, processor_id_type proc_id)
 
Elemadd_elem (Elem *elem)
 
const MeshBaseget_mesh () const
 
MeshBaseget_mesh ()
 
bool & coarsen_by_parents ()
 
Realrefine_fraction ()
 
Realcoarsen_fraction ()
 
unsigned int & max_h_level ()
 
Realcoarsen_threshold ()
 
dof_id_typenelem_target ()
 
Realabsolute_global_tolerance ()
 
unsigned char & face_level_mismatch_limit ()
 
unsigned char & edge_level_mismatch_limit ()
 
unsigned char & node_level_mismatch_limit ()
 
signed char & overrefined_boundary_limit ()
 
signed char & underrefined_boundary_limit ()
 
bool make_flags_parallel_consistent ()
 
bool get_enforce_mismatch_limit_prior_to_refinement ()
 
void set_enforce_mismatch_limit_prior_to_refinement (bool enforce)
 
bool & enforce_mismatch_limit_prior_to_refinement ()
 
const Parallel::Communicatorcomm () const
 
processor_id_type n_processors () const
 
processor_id_type processor_id () const
 

Protected Attributes

const Parallel::Communicator_communicator
 

Private Types

enum  NeighborType { POINT, EDGE }
 

Private Member Functions

 MeshRefinement (const MeshRefinement &)
 
MeshRefinementoperator= (const MeshRefinement &)
 
bool _coarsen_elements ()
 
bool _refine_elements ()
 
void _smooth_flags (bool refining, bool coarsening)
 
bool limit_level_mismatch_at_node (const unsigned int max_mismatch)
 
bool limit_level_mismatch_at_edge (const unsigned int max_mismatch)
 
bool limit_overrefined_boundary (const signed char max_mismatch)
 
bool limit_underrefined_boundary (const signed char max_mismatch)
 
bool eliminate_unrefined_patches ()
 
void create_parent_error_vector (const ErrorVector &error_per_cell, ErrorVector &error_per_parent, Real &parent_error_min, Real &parent_error_max)
 
void update_nodes_map ()
 
bool make_coarsening_compatible ()
 
bool make_refinement_compatible ()
 
Elemtopological_neighbor (Elem *elem, const PointLocatorBase *point_locator, const unsigned int side)
 
bool has_topological_neighbor (const Elem *elem, const PointLocatorBase *point_locator, const Elem *neighbor)
 
bool enforce_mismatch_limit_prior_to_refinement (Elem *elem, NeighborType nt, unsigned max_mismatch)
 

Private Attributes

TopologyMap _new_nodes_map
 
MeshBase_mesh
 
bool _use_member_parameters
 
bool _coarsen_by_parents
 
Real _refine_fraction
 
Real _coarsen_fraction
 
unsigned int _max_h_level
 
Real _coarsen_threshold
 
dof_id_type _nelem_target
 
Real _absolute_global_tolerance
 
unsigned char _face_level_mismatch_limit
 
unsigned char _edge_level_mismatch_limit
 
unsigned char _node_level_mismatch_limit
 
signed char _overrefined_boundary_limit
 
signed char _underrefined_boundary_limit
 
bool _enforce_mismatch_limit_prior_to_refinement
 
PeriodicBoundaries_periodic_boundaries
 

Detailed Description

Responsible for mesh refinement algorithms and data.

This is the MeshRefinement class. This class implements adaptive mesh refinement algorithms for a MeshBase.

Author
Benjamin S. Kirk
Date
2002-2007

Definition at line 58 of file mesh_refinement.h.

Member Enumeration Documentation

This helper function enforces the desired mismatch limits prior to refinement. It is called from the MeshRefinement::limit_level_mismatch_at_edge() and MeshRefinement::limit_level_mismatch_at_node() functions. Returns true if this enforcement caused the refinement flags for elem to change, false otherwise.

Enumerator
POINT 
EDGE 

Definition at line 840 of file mesh_refinement.h.

Constructor & Destructor Documentation

libMesh::MeshRefinement::MeshRefinement ( MeshBase mesh)
explicit

Constructor.

Definition at line 54 of file mesh_refinement.C.

References _periodic_boundaries, and set_periodic_boundaries_ptr().

54  :
55  ParallelObject(m),
56  _mesh(m),
58  _coarsen_by_parents(false),
59  _refine_fraction(0.3),
60  _coarsen_fraction(0.0),
63  _nelem_target(0),
71 #ifdef LIBMESH_ENABLE_PERIODIC
73 #endif
74 {
75 }
76 
77 
78 
79 #ifdef LIBMESH_ENABLE_PERIODIC
80 void MeshRefinement::set_periodic_boundaries_ptr(PeriodicBoundaries * pb_ptr)
81 {
82  _periodic_boundaries = pb_ptr;
83 }
ParallelObject(const Parallel::Communicator &comm_in)
const unsigned int invalid_uint
Definition: libmesh.h:184
const class libmesh_nullptr_t libmesh_nullptr
PeriodicBoundaries * _periodic_boundaries
signed char _underrefined_boundary_limit
unsigned char _face_level_mismatch_limit
signed char _overrefined_boundary_limit
bool _enforce_mismatch_limit_prior_to_refinement
unsigned char _node_level_mismatch_limit
unsigned char _edge_level_mismatch_limit
void set_periodic_boundaries_ptr(PeriodicBoundaries *pb_ptr)
libMesh::MeshRefinement::MeshRefinement ( const MeshRefinement )
private
libMesh::MeshRefinement::~MeshRefinement ( )

Destructor. Deletes all the elements that are currently stored.

Definition at line 88 of file mesh_refinement.C.

References clear().

Referenced by libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

89 {
90  this->clear();
91 }

Member Function Documentation

bool libMesh::MeshRefinement::_coarsen_elements ( )
private

Coarsens user-requested elements. Both coarsen_elements and refine_elements used to be in the public interface for the MeshRefinement object. Unfortunately, without proper preparation (make_refinement_compatible, make_coarsening_compatible) at least coarsen_elements() did not work alone. By making them private, we signal to the user that they are not part of the interface.

It is possible that for a given set of refinement flags there is actually no change upon calling this member function. Consequently, this function returns true if the mesh actually changed (hence data needs to be projected) and false otherwise.

Definition at line 1370 of file mesh_refinement.C.

References _mesh, libMesh::Elem::active(), clear(), libMesh::Elem::COARSEN, libMesh::Elem::coarsen(), libMesh::Elem::COARSEN_INACTIVE, libMesh::ParallelObject::comm(), libMesh::Elem::DO_NOTHING, libMesh::MeshBase::elements_begin(), libMesh::MeshBase::elements_end(), end, libMesh::MeshBase::get_boundary_info(), libMesh::MeshBase::is_serial(), libMesh::Elem::JUST_COARSENED, libMesh::Elem::level(), libMesh::libmesh_assert(), libMesh::MeshCommunication::make_nodes_parallel_consistent(), libMesh::MeshCommunication::make_p_levels_parallel_consistent(), libMesh::Parallel::Communicator::max(), libMesh::Elem::nullify_neighbors(), libMesh::Elem::p_level(), libMesh::Elem::p_refinement_flag(), libMesh::Elem::refinement_flag(), libMesh::BoundaryInfo::remove(), libMesh::MeshCommunication::send_coarse_ghosts(), libMesh::Elem::set_p_level(), libMesh::Elem::set_p_refinement_flag(), update_nodes_map(), and libMesh::MeshBase::update_parallel_id_counts().

Referenced by coarsen_elements(), get_mesh(), refine_and_coarsen_elements(), and uniformly_coarsen().

1371 {
1372  // This function must be run on all processors at once
1373  parallel_object_only();
1374 
1375  LOG_SCOPE ("_coarsen_elements()", "MeshRefinement");
1376 
1377  // Flags indicating if this call actually changes the mesh
1378  bool mesh_changed = false;
1379  bool mesh_p_changed = false;
1380 
1381  // Clear the unused_elements data structure.
1382  // The elements have been packed since it was built,
1383  // so there are _no_ unused elements. We cannot trust
1384  // any iterators currently in this data structure.
1385  // _unused_elements.clear();
1386 
1387  // Loop over the elements first to determine if the mesh will
1388  // undergo h-coarsening. If it will, then we'll need to communicate
1389  // more ghosted elements. We need to communicate them *before* we
1390  // do the coarsening; otherwise it is possible to coarsen away a
1391  // one-element-thick layer partition and leave the partitions on
1392  // either side unable to figure out how to talk to each other.
1393  for (MeshBase::element_iterator
1394  it = _mesh.elements_begin(),
1395  end = _mesh.elements_end();
1396  it != end; ++it)
1397  {
1398  Elem * elem = *it;
1399  if (elem->refinement_flag() == Elem::COARSEN)
1400  {
1401  mesh_changed = true;
1402  break;
1403  }
1404  }
1405 
1406  // If the mesh changed on any processor, it changed globally
1407  this->comm().max(mesh_changed);
1408 
1409  // And then we may need to widen the ghosting layers.
1410  if (mesh_changed)
1411  MeshCommunication().send_coarse_ghosts(_mesh);
1412 
1413  for (MeshBase::element_iterator
1414  it = _mesh.elements_begin(),
1415  end = _mesh.elements_end();
1416  it != end; ++it)
1417  {
1418  Elem * elem = *it;
1419 
1420  // active elements flagged for coarsening will
1421  // no longer be deleted until MeshRefinement::contract()
1422  if (elem->refinement_flag() == Elem::COARSEN)
1423  {
1424  // Huh? no level-0 element should be active
1425  // and flagged for coarsening.
1426  libmesh_assert_not_equal_to (elem->level(), 0);
1427 
1428  // Remove this element from any neighbor
1429  // lists that point to it.
1430  elem->nullify_neighbors();
1431 
1432  // Remove any boundary information associated
1433  // with this element
1434  _mesh.get_boundary_info().remove (elem);
1435 
1436  // Add this iterator to the _unused_elements
1437  // data structure so we might fill it.
1438  // The _unused_elements optimization is currently off.
1439  // _unused_elements.push_back (it);
1440 
1441  // Don't delete the element until
1442  // MeshRefinement::contract()
1443  // _mesh.delete_elem(elem);
1444  }
1445 
1446  // inactive elements flagged for coarsening
1447  // will become active
1448  else if (elem->refinement_flag() == Elem::COARSEN_INACTIVE)
1449  {
1450  elem->coarsen();
1451  libmesh_assert (elem->active());
1452 
1453  // the mesh has certainly changed
1454  mesh_changed = true;
1455  }
1456  if (elem->p_refinement_flag() == Elem::COARSEN)
1457  {
1458  if (elem->p_level() > 0)
1459  {
1460  elem->set_p_refinement_flag(Elem::JUST_COARSENED);
1461  elem->set_p_level(elem->p_level() - 1);
1462  mesh_p_changed = true;
1463  }
1464  else
1465  {
1466  elem->set_p_refinement_flag(Elem::DO_NOTHING);
1467  }
1468  }
1469  }
1470 
1471  this->comm().max(mesh_p_changed);
1472 
1473  // And we may need to update DistributedMesh values reflecting the changes
1474  if (mesh_changed)
1476 
1477  // Node processor ids may need to change if an element of that id
1478  // was coarsened away
1479  if (mesh_changed && !_mesh.is_serial())
1480  {
1481  // Update the _new_nodes_map so that processors can
1482  // find requested nodes
1483  this->update_nodes_map ();
1484 
1485  MeshCommunication().make_nodes_parallel_consistent (_mesh);
1486 
1487  // Clear the _new_nodes_map
1488  this->clear();
1489 
1490 #ifdef DEBUG
1491  MeshTools::libmesh_assert_valid_procids<Node>(_mesh);
1492 #endif
1493  }
1494 
1495  // If p levels changed all we need to do is make sure that parent p
1496  // levels changed in sync
1497  if (mesh_p_changed && !_mesh.is_serial())
1498  {
1499  MeshCommunication().make_p_levels_parallel_consistent (_mesh);
1500  }
1501 
1502  return (mesh_changed || mesh_p_changed);
1503 }
const BoundaryInfo & get_boundary_info() const
Definition: mesh_base.h:111
virtual bool is_serial() const
Definition: mesh_base.h:134
void remove(const Node *node)
IterBase * end
libmesh_assert(j)
virtual element_iterator elements_begin()=0
virtual void update_parallel_id_counts()=0
virtual element_iterator elements_end()=0
const Parallel::Communicator & comm() const
bool libMesh::MeshRefinement::_refine_elements ( )
private

Refines user-requested elements.

It is possible that for a given set of refinement flags there is actually no change upon calling this member function. Consequently, this function returns true if the mesh actually changed (hence data needs to be projected) and false otherwise.

Definition at line 1507 of file mesh_refinement.C.

References _mesh, libMesh::Elem::active(), libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), libMesh::MeshBase::active_local_elements_begin(), libMesh::MeshBase::active_local_elements_end(), libMesh::MeshBase::active_not_local_elements_begin(), libMesh::MeshBase::active_not_local_elements_end(), clear(), libMesh::ParallelObject::comm(), libMesh::MeshBase::elements_begin(), libMesh::MeshBase::elements_end(), end, libMesh::MeshBase::is_replicated(), libMesh::Elem::JUST_REFINED, libMesh::MeshBase::libmesh_assert_valid_parallel_ids(), libMesh::MeshCommunication::make_elems_parallel_consistent(), libMesh::MeshCommunication::make_new_nodes_parallel_consistent(), libMesh::MeshCommunication::make_p_levels_parallel_consistent(), libMesh::Parallel::Communicator::max(), libMesh::Elem::p_level(), libMesh::Elem::p_refinement_flag(), libMesh::Elem::REFINE, libMesh::Elem::refinement_flag(), libMesh::Elem::set_p_level(), libMesh::Elem::set_p_refinement_flag(), update_nodes_map(), and libMesh::MeshBase::update_parallel_id_counts().

Referenced by get_mesh(), refine_and_coarsen_elements(), refine_elements(), and uniformly_refine().

1508 {
1509  // This function must be run on all processors at once
1510  parallel_object_only();
1511 
1512  // Update the _new_nodes_map so that elements can
1513  // find nodes to connect to.
1514  this->update_nodes_map ();
1515 
1516  LOG_SCOPE ("_refine_elements()", "MeshRefinement");
1517 
1518  // Iterate over the elements, counting the elements
1519  // flagged for h refinement.
1520  dof_id_type n_elems_flagged = 0;
1521 
1522  MeshBase::element_iterator it = _mesh.elements_begin();
1523  const MeshBase::element_iterator end = _mesh.elements_end();
1524 
1525  for (; it != end; ++it)
1526  {
1527  Elem * elem = *it;
1528  if (elem->refinement_flag() == Elem::REFINE)
1529  n_elems_flagged++;
1530  }
1531 
1532  // Construct a local vector of Elem * which have been
1533  // previously marked for refinement. We reserve enough
1534  // space to allow for every element to be refined.
1535  std::vector<Elem *> local_copy_of_elements;
1536  local_copy_of_elements.reserve(n_elems_flagged);
1537 
1538  // If mesh p levels changed, we might need to synchronize parent p
1539  // levels on a distributed mesh.
1540  bool mesh_p_changed = false;
1541 
1542  // Iterate over the elements, looking for elements flagged for
1543  // refinement.
1544 
1545  // If we are on a ReplicatedMesh, then we just do the refinement in
1546  // the same order on every processor and everything stays in sync.
1547 
1548  // If we are on a DistributedMesh, that's impossible.
1549  //
1550  // If the mesh is distributed, we need to make sure that if we end
1551  // up as the owner of a new node, which might happen if that node is
1552  // attached to one of our own elements, then we have given it a
1553  // legitimate node id and our own processor id. We generate
1554  // legitimate node ids and use our own processor id when we are
1555  // refining our own elements but not when we refine others'
1556  // elements. Therefore we want to refine our own elements *first*,
1557  // thereby generating all nodes which might belong to us, and then
1558  // refine others' elements *after*, thereby generating nodes with
1559  // temporary ids which we know we will discard.
1560  //
1561  // Even if the DistributedMesh is serialized, we can't just treat it
1562  // like a ReplicatedMesh, because DistributedMesh doesn't *trust*
1563  // users to refine partitioned elements in a serialized way, so it
1564  // assigns temporary ids, so we need to synchronize ids afterward to
1565  // be safe anyway, so we might as well use the distributed mesh code
1566  // path.
1567  {
1568  MeshBase::element_iterator
1569  elem_it = _mesh.active_local_elements_begin(),
1570  elem_end = _mesh.active_local_elements_end();
1571 
1572  if (_mesh.is_replicated())
1573  {
1574  elem_it = _mesh.active_elements_begin();
1575  elem_end = _mesh.active_elements_end();
1576  }
1577 
1578  for (; elem_it != elem_end; ++elem_it)
1579  {
1580  Elem * elem = *elem_it;
1581  if (elem->refinement_flag() == Elem::REFINE)
1582  local_copy_of_elements.push_back(elem);
1583  if (elem->p_refinement_flag() == Elem::REFINE &&
1584  elem->active())
1585  {
1586  elem->set_p_level(elem->p_level()+1);
1587  elem->set_p_refinement_flag(Elem::JUST_REFINED);
1588  mesh_p_changed = true;
1589  }
1590  }
1591  }
1592 
1593  if (!_mesh.is_replicated())
1594  {
1595  for (MeshBase::element_iterator
1597  elem_end = _mesh.active_not_local_elements_end();
1598  elem_it != elem_end; ++elem_it)
1599  {
1600  Elem * elem = *elem_it;
1601  if (elem->refinement_flag() == Elem::REFINE)
1602  local_copy_of_elements.push_back(elem);
1603  if (elem->p_refinement_flag() == Elem::REFINE &&
1604  elem->active())
1605  {
1606  elem->set_p_level(elem->p_level()+1);
1607  elem->set_p_refinement_flag(Elem::JUST_REFINED);
1608  mesh_p_changed = true;
1609  }
1610  }
1611  }
1612 
1613  // Now iterate over the local copies and refine each one.
1614  // This may resize the mesh's internal container and invalidate
1615  // any existing iterators.
1616 
1617  for (std::size_t e = 0; e != local_copy_of_elements.size(); ++e)
1618  local_copy_of_elements[e]->refine(*this);
1619 
1620  // The mesh changed if there were elements h refined
1621  bool mesh_changed = !local_copy_of_elements.empty();
1622 
1623  // If the mesh changed on any processor, it changed globally
1624  this->comm().max(mesh_changed);
1625  this->comm().max(mesh_p_changed);
1626 
1627  // And we may need to update DistributedMesh values reflecting the changes
1628  if (mesh_changed)
1630 
1631  if (mesh_changed && !_mesh.is_replicated())
1632  {
1633  MeshCommunication().make_elems_parallel_consistent (_mesh);
1634  MeshCommunication().make_new_nodes_parallel_consistent (_mesh);
1635 #ifdef DEBUG
1637 #endif
1638  }
1639 
1640  if (mesh_p_changed && !_mesh.is_replicated())
1641  {
1642  MeshCommunication().make_p_levels_parallel_consistent (_mesh);
1643  }
1644 
1645  // Clear the _new_nodes_map and _unused_elements data structures.
1646  this->clear();
1647 
1648  return (mesh_changed || mesh_p_changed);
1649 }
virtual void libmesh_assert_valid_parallel_ids() const
Definition: mesh_base.h:916
virtual bool is_replicated() const
Definition: mesh_base.h:141
IterBase * end
virtual element_iterator elements_begin()=0
virtual element_iterator active_local_elements_begin()=0
virtual void update_parallel_id_counts()=0
virtual element_iterator elements_end()=0
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
virtual element_iterator active_not_local_elements_end()=0
const Parallel::Communicator & comm() const
virtual element_iterator active_not_local_elements_begin()=0
virtual element_iterator active_local_elements_end()=0
uint8_t dof_id_type
Definition: id_types.h:64
void libMesh::MeshRefinement::_smooth_flags ( bool  refining,
bool  coarsening 
)
private

Smooths refinement flags according to current settings.

It is possible that for a given set of refinement flags there is actually no change upon calling this member function. Consequently, this function returns true if the flags actually changed (hence data needs to be projected) and false otherwise.

Definition at line 1652 of file mesh_refinement.C.

References _edge_level_mismatch_limit, _mesh, _node_level_mismatch_limit, _overrefined_boundary_limit, _underrefined_boundary_limit, libMesh::ParallelObject::comm(), eliminate_unrefined_patches(), libMesh::MeshBase::is_serial(), libMesh::MeshTools::libmesh_assert_valid_neighbors(), limit_level_mismatch_at_edge(), limit_level_mismatch_at_node(), limit_overrefined_boundary(), limit_underrefined_boundary(), make_coarsening_compatible(), make_flags_parallel_consistent(), make_refinement_compatible(), libMesh::Parallel::Communicator::max(), and libMesh::Parallel::Communicator::min().

Referenced by coarsen_elements(), get_mesh(), refine_and_coarsen_elements(), and refine_elements().

1653 {
1654  // Smoothing can break in weird ways on a mesh with broken topology
1655 #ifdef DEBUG
1657 #endif
1658 
1659  // Repeat until flag changes match on every processor
1660  do
1661  {
1662  // Repeat until coarsening & refinement flags jive
1663  bool satisfied = false;
1664  do
1665  {
1666  // If we're refining or coarsening, hit the corresponding
1667  // face level test code. Short-circuiting || is our friend
1668  const bool coarsening_satisfied =
1669  !coarsening ||
1671 
1672  const bool refinement_satisfied =
1673  !refining ||
1675 
1676  bool smoothing_satisfied =
1677  !this->eliminate_unrefined_patches();// &&
1678 
1680  smoothing_satisfied = smoothing_satisfied &&
1682 
1684  smoothing_satisfied = smoothing_satisfied &&
1686 
1688  smoothing_satisfied = smoothing_satisfied &&
1690 
1692  smoothing_satisfied = smoothing_satisfied &&
1694 
1695  satisfied = (coarsening_satisfied &&
1696  refinement_satisfied &&
1697  smoothing_satisfied);
1698 #ifdef DEBUG
1699  bool max_satisfied = satisfied,
1700  min_satisfied = satisfied;
1701  this->comm().max(max_satisfied);
1702  this->comm().min(min_satisfied);
1703  libmesh_assert_equal_to (satisfied, max_satisfied);
1704  libmesh_assert_equal_to (satisfied, min_satisfied);
1705 #endif
1706  }
1707  while (!satisfied);
1708  }
1709  while (!_mesh.is_serial() && !this->make_flags_parallel_consistent());
1710 }
bool limit_level_mismatch_at_edge(const unsigned int max_mismatch)
virtual bool is_serial() const
Definition: mesh_base.h:134
bool limit_level_mismatch_at_node(const unsigned int max_mismatch)
bool limit_underrefined_boundary(const signed char max_mismatch)
bool limit_overrefined_boundary(const signed char max_mismatch)
signed char _underrefined_boundary_limit
signed char _overrefined_boundary_limit
unsigned char _node_level_mismatch_limit
const Parallel::Communicator & comm() const
unsigned char _edge_level_mismatch_limit
void libmesh_assert_valid_neighbors(const MeshBase &mesh, bool assert_valid_remote_elems=true)
Definition: mesh_tools.C:1686
Real & libMesh::MeshRefinement::absolute_global_tolerance ( )
inline

If absolute_global_tolerance is set to a nonzero value, methods like flag_elements_by_global_tolerance() will attempt to reduce the global error of the mesh (defined as the square root of the sum of the squares of the errors on active elements) to below this tolerance.

absolute_global_tolerance is 0 by default.

Definition at line 891 of file mesh_refinement.h.

References _absolute_global_tolerance, and _use_member_parameters.

Referenced by get_mesh().

892 {
893  _use_member_parameters = true;
895 }
Elem * libMesh::MeshRefinement::add_elem ( Elem elem)

Adds the element elem to the mesh.

Definition at line 167 of file mesh_refinement.C.

References _mesh, libMesh::MeshBase::add_elem(), and libMesh::libmesh_assert().

Referenced by libMesh::Elem::refine(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

168 {
169  libmesh_assert(elem);
170 
171 
172  // // If the unused_elements has any iterators from
173  // // old elements, take the first one
174  // if (!_unused_elements.empty())
175  // {
176  // std::vector<Elem *>::iterator it = _unused_elements.front();
177 
178  // *it = elem;
179 
180  // _unused_elements.pop_front();
181  // }
182 
183  // // Otherwise, use the conventional add method
184  // else
185  // {
186  // _mesh.add_elem (elem);
187  // }
188 
189  // The _unused_elements optimization has been turned off.
190  _mesh.add_elem (elem);
191 
192  return elem;
193 }
libmesh_assert(j)
virtual Elem * add_elem(Elem *e)=0
Node * libMesh::MeshRefinement::add_node ( Elem parent,
unsigned int  child,
unsigned int  node,
processor_id_type  proc_id 
)

Add a node to the mesh. The node should be node n of child c of parent Elem parent. The function returns a pointer to a suitable existing node, or creates a new node and returns a pointer to it if necessary. The processor_id is assigned to any newly created node.

Definition at line 102 of file mesh_refinement.C.

References _mesh, _new_nodes_map, libMesh::TopologyMap::add_node(), libMesh::MeshBase::add_point(), libMesh::TypeVector< T >::add_scaled(), libMesh::Elem::as_parent_node(), libMesh::Elem::bracketing_nodes(), libMesh::Elem::embedding_matrix(), libMesh::TopologyMap::find(), libMesh::DofObject::invalid_id, libMesh::invalid_uint, libMesh::libmesh_assert(), libMesh::Elem::n_nodes(), libMesh::Elem::node_ptr(), libMesh::MeshBase::node_ptr(), libMesh::Elem::point(), libMesh::ParallelObject::processor_id(), and libMesh::DofObject::processor_id().

Referenced by libMesh::Elem::refine(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

106 {
107  LOG_SCOPE("add_node()", "MeshRefinement");
108 
109  unsigned int parent_n = parent.as_parent_node(child, node);
110 
111  if (parent_n != libMesh::invalid_uint)
112  return parent.node_ptr(parent_n);
113 
114  const std::vector<std::pair<dof_id_type, dof_id_type> >
115  bracketing_nodes = parent.bracketing_nodes(child, node);
116 
117  // If we're not a parent node, we *must* be bracketed by at least
118  // one pair of parent nodes
119  libmesh_assert(bracketing_nodes.size());
120 
121  const dof_id_type new_node_id =
122  _new_nodes_map.find(bracketing_nodes);
123 
124  // Return the node if it already exists, but first update the
125  // processor_id if the node is now going to be attached to the
126  // element of a processor which may take ownership of it.
127  if (new_node_id != DofObject::invalid_id)
128  {
129  Node *node = _mesh.node_ptr(new_node_id);
130  if (proc_id < node->processor_id())
131  node->processor_id() = proc_id;
132  return node;
133  }
134 
135  // Otherwise we need to add a new node, with a default id and the
136  // requested processor_id. Figure out where to add the point:
137 
138  Point p; // defaults to 0,0,0
139 
140  for (unsigned int n=0; n != parent.n_nodes(); ++n)
141  {
142  // The value from the embedding matrix
143  const float em_val = parent.embedding_matrix(child,node,n);
144 
145  if (em_val != 0.)
146  {
147  p.add_scaled (parent.point(n), em_val);
148 
149  // If we'd already found the node we shouldn't be here
150  libmesh_assert_not_equal_to (em_val, 1);
151  }
152  }
153 
154  Node * new_node = _mesh.add_point (p, DofObject::invalid_id, proc_id);
155 
156  libmesh_assert(new_node);
157 
158  // Add the node to the map.
159  _new_nodes_map.add_node(*new_node, bracketing_nodes);
160 
161  // Return the address of the new node
162  return new_node;
163 }
const unsigned int invalid_uint
Definition: libmesh.h:184
dof_id_type find(dof_id_type bracket_node1, dof_id_type bracket_node2) const
Definition: topology_map.C:117
virtual const Node * node_ptr(const dof_id_type i) const =0
virtual Node * add_point(const Point &p, const dof_id_type id=DofObject::invalid_id, const processor_id_type proc_id=DofObject::invalid_processor_id)=0
libmesh_assert(j)
void add_node(const Node &mid_node, const std::vector< std::pair< dof_id_type, dof_id_type > > &bracketing_nodes)
Definition: topology_map.C:51
static const dof_id_type invalid_id
Definition: dof_object.h:335
processor_id_type processor_id() const
uint8_t dof_id_type
Definition: id_types.h:64
processor_id_type processor_id() const
Definition: dof_object.h:686
void libMesh::MeshRefinement::add_p_to_h_refinement ( )

Takes a mesh whose elements are flagged for h refinement and coarsening, and adds flags to request p refinement and coarsening of the same elements.

Definition at line 685 of file mesh_refinement_flagging.C.

References _mesh, libMesh::MeshBase::elements_begin(), and libMesh::MeshBase::elements_end().

Referenced by libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

686 {
687  MeshBase::element_iterator elem_it = _mesh.elements_begin();
688  const MeshBase::element_iterator elem_end = _mesh.elements_end();
689 
690  for ( ; elem_it != elem_end; ++elem_it)
691  (*elem_it)->set_p_refinement_flag((*elem_it)->refinement_flag());
692 }
virtual element_iterator elements_begin()=0
virtual element_iterator elements_end()=0
void libMesh::MeshRefinement::clean_refinement_flags ( )

Sets the refinement flag to Elem::DO_NOTHING for each element in the mesh.

Definition at line 696 of file mesh_refinement_flagging.C.

References _mesh, libMesh::Elem::DO_NOTHING, libMesh::MeshBase::elements_begin(), libMesh::MeshBase::elements_end(), and libMesh::Elem::INACTIVE.

Referenced by flag_elements_by_elem_fraction(), flag_elements_by_error_fraction(), flag_elements_by_nelem_target(), libMesh::EquationSystems::init(), libMesh::EquationSystems::read(), uniformly_coarsen(), uniformly_refine(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

697 {
698  // Possibly clean up the refinement flags from
699  // a previous step
700  // elem_iterator elem_it (_mesh.elements_begin());
701  // const elem_iterator elem_end(_mesh.elements_end());
702 
703  MeshBase::element_iterator elem_it = _mesh.elements_begin();
704  const MeshBase::element_iterator elem_end = _mesh.elements_end();
705 
706  for ( ; elem_it != elem_end; ++elem_it)
707  {
708  if ((*elem_it)->active())
709  {
710  (*elem_it)->set_refinement_flag(Elem::DO_NOTHING);
711  (*elem_it)->set_p_refinement_flag(Elem::DO_NOTHING);
712  }
713  else
714  {
715  (*elem_it)->set_refinement_flag(Elem::INACTIVE);
716  (*elem_it)->set_p_refinement_flag(Elem::INACTIVE);
717  }
718  }
719 }
virtual element_iterator elements_begin()=0
virtual element_iterator elements_end()=0
void libMesh::MeshRefinement::clear ( )

Deletes all the data that are currently stored.

Definition at line 95 of file mesh_refinement.C.

References _new_nodes_map, and libMesh::TopologyMap::clear().

Referenced by _coarsen_elements(), _refine_elements(), libMesh::MeshRefinement::ElementFlagging::~ElementFlagging(), and ~MeshRefinement().

96 {
98 }
bool & libMesh::MeshRefinement::coarsen_by_parents ( )
inline

If coarsen_by_parents is true, complete groups of sibling elements (elements with the same parent) will be flagged for coarsening. This should make the coarsening more likely to occur as requested.

coarsen_by_parents is true by default.

Definition at line 855 of file mesh_refinement.h.

References _coarsen_by_parents, and _use_member_parameters.

Referenced by get_mesh().

856 {
857  _use_member_parameters = true;
858  return _coarsen_by_parents;
859 }
bool libMesh::MeshRefinement::coarsen_elements ( )

Only coarsens the user-requested elements. Some elements will not be coarsened to satisfy the level one rule. It is possible that for a given set of refinement flags there is actually no change upon calling this member function. Consequently, this function returns true if the mesh actually changed (hence data needs to be projected) and false otherwise.

This function used to take an argument, maintain_level_one - new code should use face_level_mismatch_limit() instead.

Definition at line 600 of file mesh_refinement.C.

References _coarsen_elements(), _face_level_mismatch_limit, _mesh, _smooth_flags(), libMesh::Elem::active(), libMesh::Elem::DO_NOTHING, libMesh::MeshBase::elements_begin(), libMesh::MeshBase::elements_end(), libMesh::Elem::INACTIVE, libMesh::Elem::JUST_REFINED, libMesh::libmesh_assert(), make_coarsening_compatible(), make_flags_parallel_consistent(), libMesh::out, libMesh::MeshBase::prepare_for_use(), libMesh::Elem::refinement_flag(), libMesh::Elem::set_p_refinement_flag(), libMesh::Elem::set_refinement_flag(), and test_level_one().

Referenced by libMesh::EquationSystems::reinit(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

601 {
602  // This function must be run on all processors at once
603  parallel_object_only();
604 
605  // We can't yet turn a non-level-one mesh into a level-one mesh
608 
609  // Possibly clean up the refinement flags from
610  // a previous step
611  MeshBase::element_iterator elem_it = _mesh.elements_begin();
612  const MeshBase::element_iterator elem_end = _mesh.elements_end();
613 
614  for ( ; elem_it != elem_end; ++elem_it)
615  {
616  // Pointer to the element
617  Elem * elem = *elem_it;
618 
619  // Set refinement flag to INACTIVE if the
620  // element isn't active
621  if ( !elem->active())
622  {
623  elem->set_refinement_flag(Elem::INACTIVE);
624  elem->set_p_refinement_flag(Elem::INACTIVE);
625  }
626 
627  // This might be left over from the last step
628  if (elem->refinement_flag() == Elem::JUST_REFINED)
629  elem->set_refinement_flag(Elem::DO_NOTHING);
630  }
631 
632  // Parallel consistency has to come first, or coarsening
633  // along processor boundaries might occasionally be falsely
634  // prevented
635  bool flags_were_consistent = this->make_flags_parallel_consistent();
636 
637  // In theory, we should be able to remove the above call, which can
638  // be expensive and should be unnecessary. In practice, doing
639  // consistent flagging in parallel is hard, it's impossible to
640  // verify at the library level if it's being done by user code, and
641  // we don't want to abort large parallel runs in opt mode... but we
642  // do want to warn that they should be fixed.
643  libmesh_assert(flags_were_consistent);
644  if (!flags_were_consistent)
645  {
646  libMesh::out << "Refinement flags were not consistent between processors!\n"
647  << "Correcting and continuing.";
648  }
649 
650  // Smooth coarsening flags
651  _smooth_flags(false, true);
652 
653  // Coarsen the flagged elements.
654  const bool mesh_changed =
655  this->_coarsen_elements ();
656 
660  // FIXME: This won't pass unless we add a redundant find_neighbors()
661  // call or replace find_neighbors() with on-the-fly neighbor updating
662  // libmesh_assert(!this->eliminate_unrefined_patches());
663 
664  // We can't contract the mesh ourselves anymore - a System might
665  // need to restrict old coefficient vectors first
666  // _mesh.contract();
667 
668  // Finally, the new mesh may need to be prepared for use
669  if (mesh_changed)
670  _mesh.prepare_for_use (/*skip_renumber =*/false);
671 
672  return mesh_changed;
673 }
libmesh_assert(j)
virtual element_iterator elements_begin()=0
bool test_level_one(bool libmesh_assert_yes=false)
unsigned char _face_level_mismatch_limit
virtual element_iterator elements_end()=0
void prepare_for_use(const bool skip_renumber_nodes_and_elements=false, const bool skip_find_neighbors=false)
Definition: mesh_base.C:174
void _smooth_flags(bool refining, bool coarsening)
OStreamProxy out(std::cout)
Real & libMesh::MeshRefinement::coarsen_fraction ( )
inline

The coarsen_fraction sets either a desired target or a desired maximum number of elements to flag for coarsening, depending on which flag_elements_by method is called.

coarsen_fraction must be in $ [0,1] $, and is 0 by default.

Definition at line 867 of file mesh_refinement.h.

References _coarsen_fraction, and _use_member_parameters.

Referenced by get_mesh(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

868 {
869  _use_member_parameters = true;
870  return _coarsen_fraction;
871 }
Real & libMesh::MeshRefinement::coarsen_threshold ( )
inline

The coarsen_threshold provides hysteresis in AMR/C strategies. Refinement of elements with error estimate E will be done even at the expense of coarsening elements whose children's accumulated error does not exceed coarsen_threshold * E.

coarsen_threshold must be in $ [0,1] $, and is 0.1 by default.

Definition at line 879 of file mesh_refinement.h.

References _coarsen_threshold, and _use_member_parameters.

Referenced by get_mesh().

880 {
881  _use_member_parameters = true;
882  return _coarsen_threshold;
883 }
const Parallel::Communicator& libMesh::ParallelObject::comm ( ) const
inlineinherited
Returns
a reference to the Parallel::Communicator object used by this mesh.

Definition at line 87 of file parallel_object.h.

References libMesh::ParallelObject::_communicator.

Referenced by libMesh::__libmesh_petsc_diff_solver_monitor(), libMesh::__libmesh_petsc_diff_solver_residual(), libMesh::__libmesh_petsc_snes_jacobian(), libMesh::__libmesh_petsc_snes_postcheck(), libMesh::__libmesh_petsc_snes_residual(), libMesh::__libmesh_tao_equality_constraints(), libMesh::__libmesh_tao_equality_constraints_jacobian(), libMesh::__libmesh_tao_gradient(), libMesh::__libmesh_tao_hessian(), libMesh::__libmesh_tao_inequality_constraints(), libMesh::__libmesh_tao_inequality_constraints_jacobian(), libMesh::__libmesh_tao_objective(), _coarsen_elements(), libMesh::ExactSolution::_compute_error(), libMesh::ParmetisPartitioner::_do_repartition(), libMesh::UniformRefinementEstimator::_estimate_error(), libMesh::BoundaryInfo::_find_id_maps(), libMesh::PetscLinearSolver< T >::_petsc_shell_matrix_get_diagonal(), libMesh::SlepcEigenSolver< T >::_petsc_shell_matrix_get_diagonal(), libMesh::PetscLinearSolver< T >::_petsc_shell_matrix_mult(), libMesh::SlepcEigenSolver< T >::_petsc_shell_matrix_mult(), libMesh::PetscLinearSolver< T >::_petsc_shell_matrix_mult_add(), libMesh::EquationSystems::_read_impl(), _refine_elements(), _smooth_flags(), libMesh::ImplicitSystem::add_matrix(), libMesh::System::add_vector(), libMesh::EigenSparseLinearSolver< T >::adjoint_solve(), libMesh::UnstructuredMesh::all_second_order(), libMesh::MeshTools::Modification::all_tri(), libMesh::LaplaceMeshSmoother::allgather_graph(), libMesh::FEMSystem::assemble_qoi(), libMesh::MeshCommunication::assign_global_indices(), libMesh::ParmetisPartitioner::assign_partitioning(), libMesh::DofMap::attach_matrix(), libMesh::Parallel::BinSorter< KeyType, IdxType >::binsort(), libMesh::Parallel::Sort< KeyType, IdxType >::binsort(), libMesh::MeshTools::bounding_box(), libMesh::MeshCommunication::broadcast(), libMesh::SparseMatrix< T >::build(), libMesh::MeshTools::Generation::build_extrusion(), libMesh::Parallel::Histogram< KeyType, IdxType >::build_histogram(), libMesh::PetscNonlinearSolver< T >::build_mat_null_space(), libMesh::BoundaryInfo::build_node_list_from_side_list(), libMesh::EquationSystems::build_parallel_solution_vector(), libMesh::MeshBase::cache_elem_dims(), libMesh::System::calculate_norm(), libMesh::DofMap::check_dirichlet_bcid_consistency(), libMesh::DistributedVector< T >::clone(), libMesh::EigenSparseVector< T >::clone(), libMesh::LaspackVector< T >::clone(), libMesh::EpetraVector< T >::clone(), libMesh::PetscVector< T >::clone(), libMesh::EpetraVector< T >::close(), libMesh::Parallel::Sort< KeyType, IdxType >::communicate_bins(), 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(), create_parent_error_vector(), libMesh::MeshCommunication::delete_remote_elements(), libMesh::DofMap::distribute_dofs(), DMlibMeshFunction(), DMlibMeshJacobian(), DMlibMeshSetSystem_libMesh(), DMVariableBounds_libMesh(), eliminate_unrefined_patches(), libMesh::EpetraVector< T >::EpetraVector(), libMesh::WeightedPatchRecoveryErrorEstimator::estimate_error(), libMesh::PatchRecoveryErrorEstimator::estimate_error(), libMesh::JumpErrorEstimator::estimate_error(), libMesh::AdjointRefinementEstimator::estimate_error(), libMesh::ExactErrorEstimator::estimate_error(), flag_elements_by_elem_fraction(), flag_elements_by_error_fraction(), flag_elements_by_nelem_target(), libMesh::MeshCommunication::gather(), libMesh::MeshCommunication::gather_neighboring_elements(), libMesh::CondensedEigenSystem::get_eigenpair(), libMesh::DofMap::get_info(), libMesh::ImplicitSystem::get_linear_solver(), libMesh::EquationSystems::get_solution(), libMesh::LocationMap< T >::init(), libMesh::PetscDiffSolver::init(), libMesh::TimeSolver::init(), libMesh::TopologyMap::init(), libMesh::TaoOptimizationSolver< T >::init(), libMesh::PetscNonlinearSolver< T >::init(), libMesh::DistributedVector< T >::init(), libMesh::EpetraVector< T >::init(), libMesh::PetscVector< T >::init(), libMesh::SystemSubsetBySubdomain::init(), libMesh::EigenSystem::init_data(), libMesh::EigenSystem::init_matrices(), libMesh::ParmetisPartitioner::initialize(), libMesh::OptimizationSystem::initialize_equality_constraints_storage(), libMesh::OptimizationSystem::initialize_inequality_constraints_storage(), libMesh::MeshTools::libmesh_assert_parallel_consistent_procids< Elem >(), libMesh::MeshTools::libmesh_assert_parallel_consistent_procids< Node >(), libMesh::MeshTools::libmesh_assert_topology_consistent_procids< Node >(), libMesh::MeshTools::libmesh_assert_valid_boundary_ids(), libMesh::MeshTools::libmesh_assert_valid_dof_ids(), libMesh::MeshTools::libmesh_assert_valid_neighbors(), libMesh::DistributedMesh::libmesh_assert_valid_parallel_flags(), libMesh::DistributedMesh::libmesh_assert_valid_parallel_object_ids(), libMesh::DistributedMesh::libmesh_assert_valid_parallel_p_levels(), libMesh::MeshTools::libmesh_assert_valid_refinement_flags(), libMesh::MeshTools::libmesh_assert_valid_unique_ids(), limit_level_mismatch_at_edge(), limit_level_mismatch_at_node(), limit_overrefined_boundary(), limit_underrefined_boundary(), make_coarsening_compatible(), libMesh::MeshCommunication::make_elems_parallel_consistent(), make_flags_parallel_consistent(), libMesh::MeshCommunication::make_new_node_proc_ids_parallel_consistent(), libMesh::MeshCommunication::make_new_nodes_parallel_consistent(), libMesh::MeshCommunication::make_node_ids_parallel_consistent(), libMesh::MeshCommunication::make_node_proc_ids_parallel_consistent(), libMesh::MeshCommunication::make_node_unique_ids_parallel_consistent(), libMesh::MeshCommunication::make_nodes_parallel_consistent(), libMesh::MeshCommunication::make_p_levels_parallel_consistent(), make_refinement_compatible(), libMesh::DistributedVector< T >::max(), libMesh::FEMSystem::mesh_position_set(), libMesh::MeshSerializer::MeshSerializer(), libMesh::DistributedVector< T >::min(), libMesh::DistributedMesh::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::BoundaryInfo::n_shellface_conds(), libMesh::DistributedMesh::parallel_max_elem_id(), libMesh::DistributedMesh::parallel_max_node_id(), libMesh::ReplicatedMesh::parallel_max_unique_id(), libMesh::DistributedMesh::parallel_max_unique_id(), libMesh::DistributedMesh::parallel_n_elem(), libMesh::DistributedMesh::parallel_n_nodes(), libMesh::SparsityPattern::Build::parallel_sync(), libMesh::MeshTools::paranoid_n_levels(), libMesh::Partitioner::partition(), libMesh::MetisPartitioner::partition_range(), libMesh::Partitioner::partition_unpartitioned_elements(), libMesh::petsc_auto_fieldsplit(), libMesh::System::point_gradient(), libMesh::System::point_hessian(), libMesh::System::point_value(), libMesh::MeshBase::prepare_for_use(), libMesh::SparseMatrix< T >::print(), libMesh::MeshTools::processor_bounding_box(), libMesh::Nemesis_IO::read(), libMesh::XdrIO::read(), libMesh::XdrIO::read_serialized_bc_names(), libMesh::XdrIO::read_serialized_bcs_helper(), libMesh::XdrIO::read_serialized_connectivity(), libMesh::XdrIO::read_serialized_nodes(), libMesh::XdrIO::read_serialized_nodesets(), libMesh::XdrIO::read_serialized_subdomain_names(), libMesh::MeshBase::recalculate_n_partitions(), libMesh::MeshCommunication::redistribute(), libMesh::DistributedMesh::renumber_dof_objects(), libMesh::MeshCommunication::send_coarse_ghosts(), libMesh::Partitioner::set_node_processor_ids(), libMesh::DofMap::set_nonlocal_dof_objects(), libMesh::Partitioner::set_parent_processor_ids(), libMesh::LaplaceMeshSmoother::smooth(), libMesh::Parallel::Sort< KeyType, IdxType >::sort(), libMesh::MeshTools::subdomain_bounding_box(), libMesh::MeshBase::subdomain_ids(), libMesh::BoundaryInfo::sync(), libMesh::Parallel::sync_element_data_by_parent_id(), libMesh::Parallel::sync_node_data_by_element_id(), test_level_one(), test_unflagged(), libMesh::MeshTools::total_weight(), libMesh::NameBasedIO::write(), libMesh::XdrIO::write(), libMesh::XdrIO::write_serialized_bcs_helper(), libMesh::XdrIO::write_serialized_connectivity(), libMesh::XdrIO::write_serialized_nodes(), libMesh::XdrIO::write_serialized_nodesets(), libMesh::DistributedVector< T >::zero_clone(), libMesh::LaspackVector< T >::zero_clone(), libMesh::EigenSparseVector< T >::zero_clone(), libMesh::EpetraVector< T >::zero_clone(), and libMesh::PetscVector< T >::zero_clone().

88  { return _communicator; }
const Parallel::Communicator & _communicator
void libMesh::MeshRefinement::create_parent_error_vector ( const ErrorVector error_per_cell,
ErrorVector error_per_parent,
Real parent_error_min,
Real parent_error_max 
)
private

Calculates the error on all coarsenable parents. error_per_parent[parent_id] stores this error if parent_id corresponds to a coarsenable parent, and stores -1 otherwise.

Definition at line 197 of file mesh_refinement.C.

References _mesh, libMesh::MeshBase::active_local_elements_begin(), libMesh::MeshBase::active_local_elements_end(), libMesh::ParallelObject::comm(), libMesh::DofObject::id(), libMesh::libmesh_assert(), std::max(), std::min(), libMesh::Parallel::Communicator::min(), libMesh::Elem::parent(), libMesh::Parallel::Communicator::sum(), and libMesh::Parallel::verify().

Referenced by flag_elements_by_elem_fraction(), flag_elements_by_error_fraction(), flag_elements_by_error_tolerance(), flag_elements_by_nelem_target(), and get_mesh().

201 {
202  // This function must be run on all processors at once
203  parallel_object_only();
204 
205  // Make sure the input error vector is valid
206 #ifdef DEBUG
207  for (std::size_t i=0; i != error_per_cell.size(); ++i)
208  {
209  libmesh_assert_greater_equal (error_per_cell[i], 0);
210  // isnan() isn't standard C++ yet
211 #ifdef isnan
212  libmesh_assert(!isnan(error_per_cell[i]));
213 #endif
214  }
215 
216  // Use a reference to std::vector to avoid confusing
217  // this->comm().verify
218  std::vector<ErrorVectorReal> & epc = error_per_parent;
219  libmesh_assert(this->comm().verify(epc));
220 #endif // #ifdef DEBUG
221 
222  // error values on uncoarsenable elements will be left at -1
223  error_per_parent.clear();
224  error_per_parent.resize(error_per_cell.size(), 0.0);
225 
226  {
227  // Find which elements are uncoarsenable
228  MeshBase::element_iterator elem_it = _mesh.active_local_elements_begin();
229  const MeshBase::element_iterator elem_end = _mesh.active_local_elements_end();
230  for (; elem_it != elem_end; ++elem_it)
231  {
232  Elem * elem = *elem_it;
233  Elem * parent = elem->parent();
234 
235  // Active elements are uncoarsenable
236  error_per_parent[elem->id()] = -1.0;
237 
238  // Grandparents and up are uncoarsenable
239  while (parent)
240  {
241  parent = parent->parent();
242  if (parent)
243  {
244  const dof_id_type parentid = parent->id();
245  libmesh_assert_less (parentid, error_per_parent.size());
246  error_per_parent[parentid] = -1.0;
247  }
248  }
249  }
250 
251  // Sync between processors.
252  // Use a reference to std::vector to avoid confusing
253  // this->comm().min
254  std::vector<ErrorVectorReal> & epp = error_per_parent;
255  this->comm().min(epp);
256  }
257 
258  // The parent's error is defined as the square root of the
259  // sum of the children's errors squared, so errors that are
260  // Hilbert norms remain Hilbert norms.
261  //
262  // Because the children may be on different processors, we
263  // calculate local contributions to the parents' errors squared
264  // first, then sum across processors and take the square roots
265  // second.
266  {
267  MeshBase::element_iterator elem_it = _mesh.active_local_elements_begin();
268  const MeshBase::element_iterator elem_end = _mesh.active_local_elements_end();
269 
270  for (; elem_it != elem_end; ++elem_it)
271  {
272  Elem * elem = *elem_it;
273  Elem * parent = elem->parent();
274 
275  // Calculate each contribution to parent cells
276  if (parent)
277  {
278  const dof_id_type parentid = parent->id();
279  libmesh_assert_less (parentid, error_per_parent.size());
280 
281  // If the parent has grandchildren we won't be able to
282  // coarsen it, so forget it. Otherwise, add this child's
283  // contribution to the sum of the squared child errors
284  if (error_per_parent[parentid] != -1.0)
285  error_per_parent[parentid] += (error_per_cell[elem->id()] *
286  error_per_cell[elem->id()]);
287  }
288  }
289  }
290 
291  // Sum the vector across all processors
292  this->comm().sum(static_cast<std::vector<ErrorVectorReal> &>(error_per_parent));
293 
294  // Calculate the min and max as we loop
295  parent_error_min = std::numeric_limits<double>::max();
296  parent_error_max = 0.;
297 
298  for (std::size_t i = 0; i != error_per_parent.size(); ++i)
299  {
300  // If this element isn't a coarsenable parent with error, we
301  // have nothing to do. Just flag it as -1 and move on
302  // Note that this->comm().sum might have left uncoarsenable
303  // elements with error_per_parent=-n_proc, so reset it to
304  // error_per_parent=-1
305  if (error_per_parent[i] < 0.)
306  {
307  error_per_parent[i] = -1.;
308  continue;
309  }
310 
311  // The error estimator might have already given us an
312  // estimate on the coarsenable parent elements; if so then
313  // we want to retain that estimate
314  if (error_per_cell[i])
315  {
316  error_per_parent[i] = error_per_cell[i];
317  continue;
318  }
319  // if not, then e_parent = sqrt(sum(e_child^2))
320  else
321  error_per_parent[i] = std::sqrt(error_per_parent[i]);
322 
323  parent_error_min = std::min (parent_error_min,
324  error_per_parent[i]);
325  parent_error_max = std::max (parent_error_max,
326  error_per_parent[i]);
327  }
328 }
long double max(long double a, double b)
libmesh_assert(j)
virtual element_iterator active_local_elements_begin()=0
bool verify(const T &r, const Communicator &comm=Communicator_World)
const Parallel::Communicator & comm() const
virtual element_iterator active_local_elements_end()=0
long double min(long double a, double b)
uint8_t dof_id_type
Definition: id_types.h:64
unsigned char & libMesh::MeshRefinement::edge_level_mismatch_limit ( )
inline

If edge_level_mismatch_limit is set to a nonzero value, then refinement and coarsening will produce meshes in which the refinement level of two edge neighbors will not differ by more than that limit. If edge_level_mismatch_limit is 0, then level differences will be unlimited.

edge_level_mismatch_limit is 0 by default.

Definition at line 902 of file mesh_refinement.h.

References _edge_level_mismatch_limit.

Referenced by get_mesh().

903 {
905 }
unsigned char _edge_level_mismatch_limit
bool libMesh::MeshRefinement::eliminate_unrefined_patches ( )
private

This algorithm selects an element for refinement if all of its neighbors are (or will be) refined. This algorithm will transform this mesh:

* o---o---o---o---o---o---o
* |   |   |   |   |   |   |
* |   |   |   |   |   |   |
* o---o---o---o---o---o---o
* |   |   |   |   |   |   |
* |   |   |   |   |   |   |
* o---o---o---o---o---o---o
* |   |   |       |   |   |
* |   |   |       |   |   |
* o---o---o       o---o---o
* |   |   |       |   |   |
* |   |   |       |   |   |
* o---o---o---o---o---o---o
* |   |   |   |   |   |   |
* |   |   |   |   |   |   |
* o---o---o---o---o---o---o
* |   |   |   |   |   |   |
* |   |   |   |   |   |   |
* o---o---o---o---o---o---o
* 

into this:

* o---o---o---o---o---o---o
* |   |   |   |   |   |   |
* |   |   |   |   |   |   |
* o---o---o---o---o---o---o
* |   |   |   |   |   |   |
* |   |   |   |   |   |   |
* o---o---o---o---o---o---o
* |   |   |   :   |   |   |
* |   |   |   :   |   |   |
* o---o---o...o...o---o---o
* |   |   |   :   |   |   |
* |   |   |   :   |   |   |
* o---o---o---o---o---o---o
* |   |   |   |   |   |   |
* |   |   |   |   |   |   |
* o---o---o---o---o---o---o
* |   |   |   |   |   |   |
* |   |   |   |   |   |   |
* o---o---o---o---o---o---o
* 

by refining the indicated element

Definition at line 418 of file mesh_refinement_smoothing.C.

References _mesh, libMesh::Elem::active(), libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), libMesh::Elem::ancestor(), libMesh::Elem::child_ptr(), libMesh::Elem::COARSEN, libMesh::Elem::COARSEN_INACTIVE, libMesh::ParallelObject::comm(), libMesh::Elem::DO_NOTHING, libMesh::Elem::INACTIVE, libMesh::Elem::level(), libMesh::libmesh_assert(), libmesh_nullptr, libMesh::Parallel::Communicator::max(), libMesh::Elem::min_new_p_level_by_neighbor(), libMesh::Elem::n_children(), libMesh::Elem::n_neighbors(), libMesh::Elem::neighbor_ptr(), libMesh::Elem::p_level(), libMesh::Elem::p_refinement_flag(), libMesh::Elem::parent(), libMesh::Elem::REFINE, libMesh::Elem::refinement_flag(), libMesh::remote_elem, libMesh::Elem::set_p_refinement_flag(), and libMesh::Elem::set_refinement_flag().

Referenced by _smooth_flags(), and get_mesh().

419 {
420  // This function must be run on all processors at once
421  parallel_object_only();
422 
423  bool flags_changed = false;
424 
425  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
426  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
427 
428  for (; elem_it != elem_end; ++elem_it)
429  {
430  Elem * elem = *elem_it;
431  // First assume that we'll have to flag this element for both h
432  // and p refinement, then change our minds if we see any
433  // neighbors that are as coarse or coarser than us.
434  bool h_flag_me = true,
435  p_flag_me = true;
436 
437 
438  // Skip the element if it is already fully flagged for refinement
439  if (elem->p_refinement_flag() == Elem::REFINE)
440  p_flag_me = false;
441  if (elem->refinement_flag() == Elem::REFINE)
442  {
443  h_flag_me = false;
444  if (!p_flag_me)
445  continue;
446  }
447  // Test the parent if that is already flagged for coarsening
448  else if (elem->refinement_flag() == Elem::COARSEN)
449  {
450  libmesh_assert(elem->parent());
451  elem = elem->parent();
452  // FIXME - this doesn't seem right - RHS
453  if (elem->refinement_flag() != Elem::COARSEN_INACTIVE)
454  continue;
455  p_flag_me = false;
456  }
457 
458  const unsigned int my_level = elem->level();
459  int my_p_adjustment = 0;
460  if (elem->p_refinement_flag() == Elem::REFINE)
461  my_p_adjustment = 1;
462  else if (elem->p_refinement_flag() == Elem::COARSEN)
463  {
464  libmesh_assert_greater (elem->p_level(), 0);
465  my_p_adjustment = -1;
466  }
467  const unsigned int my_new_p_level = elem->p_level() +
468  my_p_adjustment;
469 
470  // Check all the element neighbors
471  for (unsigned int n=0; n<elem->n_neighbors(); n++)
472  {
473  const Elem * neighbor = elem->neighbor_ptr(n);
474  // Quit if the element is on a local boundary
475  if (neighbor == libmesh_nullptr || neighbor == remote_elem)
476  {
477  h_flag_me = false;
478  p_flag_me = false;
479  break;
480  }
481  // if the neighbor will be equally or less refined than
482  // we are, then we will not become an unrefined island.
483  // So if we are still considering h refinement:
484  if (h_flag_me &&
485  // If our neighbor is already at a lower level,
486  // it can't end up at a higher level even if it
487  // is flagged for refinement once
488  ((neighbor->level() < my_level) ||
489  // If our neighbor is at the same level but isn't
490  // flagged for refinement, it won't end up at a
491  // higher level
492  ((neighbor->active()) &&
493  (neighbor->refinement_flag() != Elem::REFINE)) ||
494  // If our neighbor is currently more refined but is
495  // a parent flagged for coarsening, it will end up
496  // at the same level.
497  (neighbor->refinement_flag() == Elem::COARSEN_INACTIVE)))
498  {
499  // We've proven we won't become an unrefined island,
500  // so don't h refine to avoid that.
501  h_flag_me = false;
502 
503  // If we've also proven we don't need to p refine,
504  // we don't need to check more neighbors
505  if (!p_flag_me)
506  break;
507  }
508  if (p_flag_me)
509  {
510  // if active neighbors will have a p level
511  // equal to or lower than ours, then we do not need to p
512  // refine ourselves.
513  if (neighbor->active())
514  {
515  int p_adjustment = 0;
516  if (neighbor->p_refinement_flag() == Elem::REFINE)
517  p_adjustment = 1;
518  else if (neighbor->p_refinement_flag() == Elem::COARSEN)
519  {
520  libmesh_assert_greater (neighbor->p_level(), 0);
521  p_adjustment = -1;
522  }
523  if (my_new_p_level >= neighbor->p_level() + p_adjustment)
524  {
525  p_flag_me = false;
526  if (!h_flag_me)
527  break;
528  }
529  }
530  // If we have inactive neighbors, we need to
531  // test all their active descendants which neighbor us
532  else if (neighbor->ancestor())
533  {
534  if (neighbor->min_new_p_level_by_neighbor(elem,
535  my_new_p_level + 2) <= my_new_p_level)
536  {
537  p_flag_me = false;
538  if (!h_flag_me)
539  break;
540  }
541  }
542  }
543  }
544 
545  if (h_flag_me)
546  {
547  // Parents that would create islands should no longer
548  // coarsen
549  if (elem->refinement_flag() == Elem::COARSEN_INACTIVE)
550  {
551  for (unsigned int c=0; c<elem->n_children(); c++)
552  {
553  libmesh_assert_equal_to (elem->child_ptr(c)->refinement_flag(),
554  Elem::COARSEN);
555  elem->child_ptr(c)->set_refinement_flag(Elem::DO_NOTHING);
556  }
557  elem->set_refinement_flag(Elem::INACTIVE);
558  }
559  else
560  elem->set_refinement_flag(Elem::REFINE);
561  flags_changed = true;
562  }
563  if (p_flag_me)
564  {
565  if (elem->p_refinement_flag() == Elem::COARSEN)
566  elem->set_p_refinement_flag(Elem::DO_NOTHING);
567  else
568  elem->set_p_refinement_flag(Elem::REFINE);
569  flags_changed = true;
570  }
571  }
572 
573  // If flags changed on any processor then they changed globally
574  this->comm().max(flags_changed);
575 
576  return flags_changed;
577 }
const class libmesh_nullptr_t libmesh_nullptr
libmesh_assert(j)
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
const Parallel::Communicator & comm() const
const RemoteElem * remote_elem
Definition: remote_elem.C:57
bool & libMesh::MeshRefinement::enforce_mismatch_limit_prior_to_refinement ( )
inline

Get/set the _enforce_mismatch_limit_prior_to_refinement flag. The default value for this flag is false.

Definition at line 934 of file mesh_refinement.h.

References _enforce_mismatch_limit_prior_to_refinement.

Referenced by get_enforce_mismatch_limit_prior_to_refinement(), get_mesh(), limit_level_mismatch_at_edge(), limit_level_mismatch_at_node(), and set_enforce_mismatch_limit_prior_to_refinement().

935 {
937 }
bool _enforce_mismatch_limit_prior_to_refinement
bool libMesh::MeshRefinement::enforce_mismatch_limit_prior_to_refinement ( Elem elem,
NeighborType  nt,
unsigned  max_mismatch 
)
private

Definition at line 581 of file mesh_refinement_smoothing.C.

References _enforce_mismatch_limit_prior_to_refinement, libMesh::Elem::DO_NOTHING, EDGE, libMesh::Elem::find_edge_neighbors(), libMesh::Elem::find_point_neighbors(), libMesh::Elem::level(), libMesh::Elem::p_level(), POINT, libMesh::Elem::REFINE, libMesh::Elem::refinement_flag(), libMesh::Elem::set_p_refinement_flag(), and libMesh::Elem::set_refinement_flag().

584 {
585  // Eventual return value
586  bool flags_changed = false;
587 
588  // If we are enforcing the limit prior to refinement then we
589  // need to remove flags from any elements marked for refinement that
590  // would cause a mismatch
592  && elem->refinement_flag() == Elem::REFINE)
593  {
594  // get all the relevant neighbors since we may have to refine
595  // elements off edges or corners as well
596  std::set<const Elem *> neighbor_set;
597 
598  if (nt == POINT)
599  elem->find_point_neighbors(neighbor_set);
600  else if (nt == EDGE)
601  elem->find_edge_neighbors(neighbor_set);
602  else
603  libmesh_error_msg("Unrecognized NeighborType: " << nt);
604 
605  // Loop over the neighbors of element e
606  std::set<const Elem *>::iterator n_it = neighbor_set.begin();
607  for (; n_it != neighbor_set.end(); ++n_it)
608  {
609  const Elem * neighbor = *n_it;
610 
611  if ((elem->level() + 1 - max_mismatch) > neighbor->level())
612  {
613  elem->set_refinement_flag(Elem::DO_NOTHING);
614  flags_changed = true;
615  }
616  if ((elem->p_level() + 1 - max_mismatch) > neighbor->p_level())
617  {
618  elem->set_p_refinement_flag(Elem::DO_NOTHING);
619  flags_changed = true;
620  }
621  } // loop over edge/point neighbors
622  } // if _enforce_mismatch_limit_prior_to_refinement
623 
624  return flags_changed;
625 }
bool _enforce_mismatch_limit_prior_to_refinement
unsigned char & libMesh::MeshRefinement::face_level_mismatch_limit ( )
inline

If face_level_mismatch_limit is set to a nonzero value, then refinement and coarsening will produce meshes in which the refinement level of two face neighbors will not differ by more than that limit. If face_level_mismatch_limit is 0, then level differences will be unlimited.

face_level_mismatch_limit is 1 by default. Currently the only supported options are 0 and 1.

Definition at line 897 of file mesh_refinement.h.

References _face_level_mismatch_limit.

Referenced by get_mesh(), and libMesh::EquationSystems::reinit().

898 {
900 }
unsigned char _face_level_mismatch_limit
void libMesh::MeshRefinement::flag_elements_by ( ElementFlagging element_flagging)

Flag elements based on a function object. The class ElementFlagging defines a mechanism for implementing refinement strategies.

Definition at line 656 of file mesh_refinement_flagging.C.

References libMesh::MeshRefinement::ElementFlagging::flag_elements().

Referenced by libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

657 {
658  element_flagging.flag_elements();
659 }
void libMesh::MeshRefinement::flag_elements_by_elem_fraction ( const ErrorVector error_per_cell,
const Real  refine_fraction = 0.3,
const Real  coarsen_fraction = 0.0,
const unsigned int  max_level = libMesh::invalid_uint 
)

Flags elements for coarsening and refinement based on the computed error passed in error_per_cell. This method picks the top refine_fraction * n_elem elements for refinement and the bottom coarsen_fraction * n_elem elements for coarsening. The two fractions refine_fraction and coarsen_fraction must be in $ [0,1] $.

All the function arguments except error_per_cell have been deprecated, and will be removed in future libMesh releases - to control these parameters, set the corresponding member variables.

Definition at line 453 of file mesh_refinement_flagging.C.

References _coarsen_by_parents, _coarsen_fraction, _max_h_level, _mesh, _refine_fraction, _use_member_parameters, libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_local_elements_begin(), libMesh::MeshBase::active_local_elements_end(), libMesh::Parallel::Communicator::allgather(), clean_refinement_flags(), libMesh::Elem::COARSEN, libMesh::ParallelObject::comm(), create_parent_error_vector(), libMesh::ErrorVectorReal, libMesh::DofObject::id(), libMesh::invalid_uint, libMesh::Elem::level(), libMesh::MeshBase::mesh_dimension(), libMesh::MeshBase::n_active_elem(), libMesh::Elem::parent(), libMesh::Real, libMesh::Elem::REFINE, and libMesh::Elem::set_refinement_flag().

Referenced by libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

457 {
458  parallel_object_only();
459 
460  // The function arguments are currently just there for
461  // backwards_compatibility
463  {
464  // If the user used non-default parameters, lets warn
465  // that they're deprecated
466  if (refine_frac != 0.3 ||
467  coarsen_frac != 0.0 ||
468  max_l != libMesh::invalid_uint)
469  libmesh_deprecated();
470 
471  _refine_fraction = refine_frac;
472  _coarsen_fraction = coarsen_frac;
473  _max_h_level = max_l;
474  }
475 
476  // Check for valid fractions..
477  // The fraction values must be in [0,1]
478  libmesh_assert_greater_equal (_refine_fraction, 0);
479  libmesh_assert_less_equal (_refine_fraction, 1);
480  libmesh_assert_greater_equal (_coarsen_fraction, 0);
481  libmesh_assert_less_equal (_coarsen_fraction, 1);
482 
483  // The number of active elements in the mesh
484  const dof_id_type n_active_elem = _mesh.n_active_elem();
485 
486  // The number of elements to flag for coarsening
487  const dof_id_type n_elem_coarsen =
488  static_cast<dof_id_type>(_coarsen_fraction * n_active_elem);
489 
490  // The number of elements to flag for refinement
491  const dof_id_type n_elem_refine =
492  static_cast<dof_id_type>(_refine_fraction * n_active_elem);
493 
494 
495 
496  // Clean up the refinement flags. These could be left
497  // over from previous refinement steps.
498  this->clean_refinement_flags();
499 
500 
501  // This vector stores the error and element number for all the
502  // active elements. It will be sorted and the top & bottom
503  // elements will then be flagged for coarsening & refinement
504  std::vector<ErrorVectorReal> sorted_error;
505 
506  sorted_error.reserve (n_active_elem);
507 
508  // Loop over the active elements and create the entry
509  // in the sorted_error vector
510  MeshBase::element_iterator elem_it = _mesh.active_local_elements_begin();
511  const MeshBase::element_iterator elem_end = _mesh.active_local_elements_end();
512 
513  for (; elem_it != elem_end; ++elem_it)
514  sorted_error.push_back (error_per_cell[(*elem_it)->id()]);
515 
516  this->comm().allgather(sorted_error);
517 
518  // Now sort the sorted_error vector
519  std::sort (sorted_error.begin(), sorted_error.end());
520 
521  // If we're coarsening by parents:
522  // Create a sorted error vector with coarsenable parent elements
523  // only, sorted by lowest errors first
524  ErrorVector error_per_parent, sorted_parent_error;
526  {
527  Real parent_error_min, parent_error_max;
528 
529  create_parent_error_vector(error_per_cell,
530  error_per_parent,
531  parent_error_min,
532  parent_error_max);
533 
534  sorted_parent_error = error_per_parent;
535  std::sort (sorted_parent_error.begin(), sorted_parent_error.end());
536 
537  // All the other error values will be 0., so get rid of them.
538  sorted_parent_error.erase (std::remove(sorted_parent_error.begin(),
539  sorted_parent_error.end(), 0.),
540  sorted_parent_error.end());
541  }
542 
543 
544  ErrorVectorReal top_error= 0., bottom_error = 0.;
545 
546  // Get the maximum error value corresponding to the
547  // bottom n_elem_coarsen elements
548  if (_coarsen_by_parents && n_elem_coarsen)
549  {
550  const unsigned int dim = _mesh.mesh_dimension();
551  unsigned int twotodim = 1;
552  for (unsigned int i=0; i!=dim; ++i)
553  twotodim *= 2;
554 
555  dof_id_type n_parent_coarsen = n_elem_coarsen / (twotodim - 1);
556 
557  if (n_parent_coarsen)
558  bottom_error = sorted_parent_error[n_parent_coarsen - 1];
559  }
560  else if (n_elem_coarsen)
561  {
562  bottom_error = sorted_error[n_elem_coarsen - 1];
563  }
564 
565  if (n_elem_refine)
566  top_error = sorted_error[sorted_error.size() - n_elem_refine];
567 
568  // Finally, let's do the element flagging
569  elem_it = _mesh.active_elements_begin();
570  for (; elem_it != elem_end; ++elem_it)
571  {
572  Elem * elem = *elem_it;
573  Elem * parent = elem->parent();
574 
575  if (_coarsen_by_parents && parent && n_elem_coarsen &&
576  error_per_parent[parent->id()] <= bottom_error)
577  elem->set_refinement_flag(Elem::COARSEN);
578 
579  if (!_coarsen_by_parents && n_elem_coarsen &&
580  error_per_cell[elem->id()] <= bottom_error)
581  elem->set_refinement_flag(Elem::COARSEN);
582 
583  if (n_elem_refine &&
584  elem->level() < _max_h_level &&
585  error_per_cell[elem->id()] >= top_error)
586  elem->set_refinement_flag(Elem::REFINE);
587  }
588 }
virtual dof_id_type n_active_elem() const =0
const unsigned int invalid_uint
Definition: libmesh.h:184
void create_parent_error_vector(const ErrorVector &error_per_cell, ErrorVector &error_per_parent, Real &parent_error_min, Real &parent_error_max)
DIE A HORRIBLE DEATH HERE typedef float ErrorVectorReal
virtual element_iterator active_local_elements_begin()=0
virtual element_iterator active_elements_begin()=0
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
const Parallel::Communicator & comm() const
unsigned int mesh_dimension() const
Definition: mesh_base.C:148
virtual element_iterator active_local_elements_end()=0
uint8_t dof_id_type
Definition: id_types.h:64
void allgather(const T &send, std::vector< T > &recv) const
void libMesh::MeshRefinement::flag_elements_by_error_fraction ( const ErrorVector error_per_cell,
const Real  refine_fraction = 0.3,
const Real  coarsen_fraction = 0.0,
const unsigned int  max_level = libMesh::invalid_uint 
)

Flags elements for coarsening and refinement based on the computed error passed in error_per_cell. The two fractions refine_fraction and coarsen_fraction must be in $ [0,1] $.

All the function arguments except error_per_cell have been deprecated, and will be removed in future libMesh releases - to control these parameters, set the corresponding member variables.

Definition at line 45 of file mesh_refinement_flagging.C.

References _coarsen_by_parents, _coarsen_fraction, _max_h_level, _mesh, _refine_fraction, _use_member_parameters, libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), libMesh::MeshBase::active_local_elements_begin(), libMesh::MeshBase::active_local_elements_end(), clean_refinement_flags(), libMesh::Elem::COARSEN, libMesh::ParallelObject::comm(), create_parent_error_vector(), libMesh::ErrorVectorReal, libMesh::DofObject::id(), libMesh::invalid_uint, libMesh::Elem::level(), std::max(), libMesh::Parallel::Communicator::max(), std::min(), libMesh::Parallel::Communicator::min(), libMesh::Elem::parent(), libMesh::Real, libMesh::Elem::REFINE, and libMesh::Elem::set_refinement_flag().

Referenced by libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

49 {
50  parallel_object_only();
51 
52  // The function arguments are currently just there for
53  // backwards_compatibility
55  {
56  // If the user used non-default parameters, lets warn
57  // that they're deprecated
58  if (refine_frac != 0.3 ||
59  coarsen_frac != 0.0 ||
60  max_l != libMesh::invalid_uint)
61  libmesh_deprecated();
62 
63  _refine_fraction = refine_frac;
64  _coarsen_fraction = coarsen_frac;
65  _max_h_level = max_l;
66  }
67 
68  // Check for valid fractions..
69  // The fraction values must be in [0,1]
70  libmesh_assert_greater_equal (_refine_fraction, 0);
71  libmesh_assert_less_equal (_refine_fraction, 1);
72  libmesh_assert_greater_equal (_coarsen_fraction, 0);
73  libmesh_assert_less_equal (_coarsen_fraction, 1);
74 
75  // Clean up the refinement flags. These could be left
76  // over from previous refinement steps.
77  this->clean_refinement_flags();
78 
79  // We're getting the minimum and maximum error values
80  // for the ACTIVE elements
81  Real error_min = 1.e30;
82  Real error_max = 0.;
83 
84  // And, if necessary, for their parents
85  Real parent_error_min = 1.e30;
86  Real parent_error_max = 0.;
87 
88  // Prepare another error vector if we need to sum parent errors
89  ErrorVector error_per_parent;
91  {
92  create_parent_error_vector(error_per_cell,
93  error_per_parent,
94  parent_error_min,
95  parent_error_max);
96  }
97 
98  // We need to loop over all active elements to find the minimum
99  MeshBase::element_iterator el_it =
101  const MeshBase::element_iterator el_end =
103 
104  for (; el_it != el_end; ++el_it)
105  {
106  const dof_id_type id = (*el_it)->id();
107  libmesh_assert_less (id, error_per_cell.size());
108 
109  error_max = std::max (error_max, error_per_cell[id]);
110  error_min = std::min (error_min, error_per_cell[id]);
111  }
112  this->comm().max(error_max);
113  this->comm().min(error_min);
114 
115  // Compute the cutoff values for coarsening and refinement
116  const Real error_delta = (error_max - error_min);
117  const Real parent_error_delta = parent_error_max - parent_error_min;
118 
119  const Real refine_cutoff = (1.- _refine_fraction)*error_max;
120  const Real coarsen_cutoff = _coarsen_fraction*error_delta + error_min;
121  const Real parent_cutoff = _coarsen_fraction*parent_error_delta + error_min;
122 
123  // // Print information about the error
124  // libMesh::out << " Error Information:" << std::endl
125  // << " ------------------" << std::endl
126  // << " min: " << error_min << std::endl
127  // << " max: " << error_max << std::endl
128  // << " delta: " << error_delta << std::endl
129  // << " refine_cutoff: " << refine_cutoff << std::endl
130  // << " coarsen_cutoff: " << coarsen_cutoff << std::endl;
131 
132 
133 
134  // Loop over the elements and flag them for coarsening or
135  // refinement based on the element error
136 
137  MeshBase::element_iterator e_it =
139  const MeshBase::element_iterator e_end =
141  for (; e_it != e_end; ++e_it)
142  {
143  Elem * elem = *e_it;
144  const dof_id_type id = elem->id();
145 
146  libmesh_assert_less (id, error_per_cell.size());
147 
148  const ErrorVectorReal elem_error = error_per_cell[id];
149 
151  {
152  Elem * parent = elem->parent();
153  if (parent)
154  {
155  const dof_id_type parentid = parent->id();
156  if (error_per_parent[parentid] >= 0. &&
157  error_per_parent[parentid] <= parent_cutoff)
158  elem->set_refinement_flag(Elem::COARSEN);
159  }
160  }
161  // Flag the element for coarsening if its error
162  // is <= coarsen_fraction*delta + error_min
163  else if (elem_error <= coarsen_cutoff)
164  {
165  elem->set_refinement_flag(Elem::COARSEN);
166  }
167 
168  // Flag the element for refinement if its error
169  // is >= refinement_cutoff.
170  if (elem_error >= refine_cutoff)
171  if (elem->level() < _max_h_level)
172  elem->set_refinement_flag(Elem::REFINE);
173  }
174 }
const unsigned int invalid_uint
Definition: libmesh.h:184
void create_parent_error_vector(const ErrorVector &error_per_cell, ErrorVector &error_per_parent, Real &parent_error_min, Real &parent_error_max)
long double max(long double a, double b)
DIE A HORRIBLE DEATH HERE typedef float ErrorVectorReal
virtual element_iterator active_local_elements_begin()=0
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
const Parallel::Communicator & comm() const
virtual element_iterator active_local_elements_end()=0
long double min(long double a, double b)
uint8_t dof_id_type
Definition: id_types.h:64
void libMesh::MeshRefinement::flag_elements_by_error_tolerance ( const ErrorVector error_per_cell)

Flags elements for coarsening and refinement based on the computed error passed in error_per_cell. This method refines the worst elements with errors greater than absolute_global_tolerance / n_active_elem, flagging at most refine_fraction * n_active_elem It coarsens elements with errors less than coarsen_threshold * global_tolerance / n_active_elem, flagging at most coarsen_fraction * n_active_elem

The three fractions refine_fraction coarsen_fraction and coarsen_threshold should be in $ [0,1] $.

Definition at line 178 of file mesh_refinement_flagging.C.

References _absolute_global_tolerance, _coarsen_by_parents, _coarsen_fraction, _coarsen_threshold, _max_h_level, _mesh, _refine_fraction, libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), libMesh::Elem::COARSEN, create_parent_error_vector(), libMesh::ErrorVectorReal, libMesh::DofObject::id(), libMesh::Elem::level(), libMesh::MeshBase::n_active_elem(), libMesh::Elem::n_children(), libMesh::Elem::parent(), libMesh::Real, libMesh::Elem::REFINE, and libMesh::Elem::set_refinement_flag().

Referenced by libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

179 {
180  parallel_object_only();
181 
182  libmesh_assert_greater (_coarsen_threshold, 0);
183 
184  // Check for valid fractions..
185  // The fraction values must be in [0,1]
186  libmesh_assert_greater_equal (_refine_fraction, 0);
187  libmesh_assert_less_equal (_refine_fraction, 1);
188  libmesh_assert_greater_equal (_coarsen_fraction, 0);
189  libmesh_assert_less_equal (_coarsen_fraction, 1);
190 
191  // How much error per cell will we tolerate?
192  const Real local_refinement_tolerance =
193  _absolute_global_tolerance / std::sqrt(static_cast<Real>(_mesh.n_active_elem()));
194  const Real local_coarsening_tolerance =
195  local_refinement_tolerance * _coarsen_threshold;
196 
197  // Prepare another error vector if we need to sum parent errors
198  ErrorVector error_per_parent;
200  {
201  Real parent_error_min, parent_error_max;
202 
203  create_parent_error_vector(error_per_cell_in,
204  error_per_parent,
205  parent_error_min,
206  parent_error_max);
207  }
208 
209  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
210  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
211 
212  for (; elem_it != elem_end; ++elem_it)
213  {
214  Elem * elem = *elem_it;
215  Elem * parent = elem->parent();
216  const dof_id_type elem_number = elem->id();
217  const ErrorVectorReal elem_error = error_per_cell_in[elem_number];
218 
219  if (elem_error > local_refinement_tolerance &&
220  elem->level() < _max_h_level)
221  elem->set_refinement_flag(Elem::REFINE);
222 
223  if (!_coarsen_by_parents && elem_error <
224  local_coarsening_tolerance)
225  elem->set_refinement_flag(Elem::COARSEN);
226 
227  if (_coarsen_by_parents && parent)
228  {
229  ErrorVectorReal parent_error = error_per_parent[parent->id()];
230  if (parent_error >= 0.)
231  {
232  const Real parent_coarsening_tolerance =
233  std::sqrt(parent->n_children() *
234  local_coarsening_tolerance *
235  local_coarsening_tolerance);
236  if (parent_error < parent_coarsening_tolerance)
237  elem->set_refinement_flag(Elem::COARSEN);
238  }
239  }
240  }
241 }
virtual dof_id_type n_active_elem() const =0
void create_parent_error_vector(const ErrorVector &error_per_cell, ErrorVector &error_per_parent, Real &parent_error_min, Real &parent_error_max)
DIE A HORRIBLE DEATH HERE typedef float ErrorVectorReal
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
uint8_t dof_id_type
Definition: id_types.h:64
void libMesh::MeshRefinement::flag_elements_by_mean_stddev ( const ErrorVector error_per_cell,
const Real  refine_fraction = 1.0,
const Real  coarsen_fraction = 0.0,
const unsigned int  max_level = libMesh::invalid_uint 
)

Flags elements for coarsening and refinement based on the computed error passed in error_per_cell. This method picks the top refine_fraction * stddev + mean elements for refinement and the bottom mean - coarsen_fraction * stddev elements for coarsening. The two fractions refine_fraction and coarsen_fraction must be in $ [0,1] $.

All the function arguments except error_per_cell have been deprecated, and will be removed in future libMesh releases - to control these parameters, set the corresponding member variables.

Definition at line 592 of file mesh_refinement_flagging.C.

References _coarsen_fraction, _max_h_level, _mesh, _refine_fraction, _use_member_parameters, libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), libMesh::Elem::COARSEN, libMesh::ErrorVectorReal, libMesh::DofObject::id(), libMesh::invalid_uint, libMesh::Elem::level(), std::max(), libMesh::ErrorVector::mean(), libMesh::Real, libMesh::Elem::REFINE, libMesh::Elem::set_refinement_flag(), and libMesh::ErrorVector::variance().

Referenced by libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

596 {
597  // The function arguments are currently just there for
598  // backwards_compatibility
600  {
601  // If the user used non-default parameters, lets warn
602  // that they're deprecated
603  if (refine_frac != 0.3 ||
604  coarsen_frac != 0.0 ||
605  max_l != libMesh::invalid_uint)
606  libmesh_deprecated();
607 
608  _refine_fraction = refine_frac;
609  _coarsen_fraction = coarsen_frac;
610  _max_h_level = max_l;
611  }
612 
613  // Get the mean value from the error vector
614  const Real mean = error_per_cell.mean();
615 
616  // Get the standard deviation. This equals the
617  // square-root of the variance
618  const Real stddev = std::sqrt (error_per_cell.variance());
619 
620  // Check for valid fractions
621  libmesh_assert_greater_equal (_refine_fraction, 0);
622  libmesh_assert_less_equal (_refine_fraction, 1);
623  libmesh_assert_greater_equal (_coarsen_fraction, 0);
624  libmesh_assert_less_equal (_coarsen_fraction, 1);
625 
626  // The refine and coarsen cutoff
627  const Real refine_cutoff = mean + _refine_fraction * stddev;
628  const Real coarsen_cutoff = std::max(mean - _coarsen_fraction * stddev, 0.);
629 
630  // Loop over the elements and flag them for coarsening or
631  // refinement based on the element error
632  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
633  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
634 
635  for (; elem_it != elem_end; ++elem_it)
636  {
637  Elem * elem = *elem_it;
638  const dof_id_type id = elem->id();
639 
640  libmesh_assert_less (id, error_per_cell.size());
641 
642  const ErrorVectorReal elem_error = error_per_cell[id];
643 
644  // Possibly flag the element for coarsening ...
645  if (elem_error <= coarsen_cutoff)
646  elem->set_refinement_flag(Elem::COARSEN);
647 
648  // ... or refinement
649  if ((elem_error >= refine_cutoff) && (elem->level() < _max_h_level))
650  elem->set_refinement_flag(Elem::REFINE);
651  }
652 }
const unsigned int invalid_uint
Definition: libmesh.h:184
long double max(long double a, double b)
DIE A HORRIBLE DEATH HERE typedef float ErrorVectorReal
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
uint8_t dof_id_type
Definition: id_types.h:64
bool libMesh::MeshRefinement::flag_elements_by_nelem_target ( const ErrorVector error_per_cell)

Flags elements for coarsening and refinement based on the computed error passed in error_per_cell. This method attempts to produce a mesh with slightly more than nelem_target active elements, trading element refinement for element coarsening when their error ratios exceed coarsen_threshold. It flags no more than refine_fraction * n_elem elements for refinement and flags no more than coarsen_fraction * n_elem elements for coarsening. This method returns true if it has done all the AMR/C it can do in a single step, or false if further adaptive steps may be required to produce a mesh with a narrow error distribution and the right number of elements.

Definition at line 245 of file mesh_refinement_flagging.C.

References _coarsen_by_parents, _coarsen_fraction, _coarsen_threshold, _max_h_level, _mesh, _nelem_target, _refine_fraction, libMesh::Elem::active(), libMesh::MeshBase::active_local_elements_begin(), libMesh::MeshBase::active_local_elements_end(), libMesh::Parallel::Communicator::allgather(), libMesh::Elem::child_ptr(), clean_refinement_flags(), libMesh::Elem::COARSEN, libMesh::ParallelObject::comm(), create_parent_error_vector(), libMesh::Elem::has_children(), libMesh::Elem::level(), libMesh::libmesh_assert(), libMesh::Parallel::Communicator::max(), libMesh::MeshBase::max_elem_id(), libMesh::MeshBase::mesh_dimension(), std::min(), libMesh::MeshBase::n_active_elem(), libMesh::Elem::n_children(), libMesh::MeshBase::query_elem_ptr(), libMesh::Real, libMesh::Elem::REFINE, libMesh::remote_elem, and libMesh::Elem::set_refinement_flag().

Referenced by libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

246 {
247  parallel_object_only();
248 
249  // Check for valid fractions..
250  // The fraction values must be in [0,1]
251  libmesh_assert_greater_equal (_refine_fraction, 0);
252  libmesh_assert_less_equal (_refine_fraction, 1);
253  libmesh_assert_greater_equal (_coarsen_fraction, 0);
254  libmesh_assert_less_equal (_coarsen_fraction, 1);
255 
256  // This function is currently only coded to work when coarsening by
257  // parents - it's too hard to guess how many coarsenings will be
258  // performed otherwise.
260 
261  // The number of active elements in the mesh - hopefully less than
262  // 2 billion on 32 bit machines
263  const dof_id_type n_active_elem = _mesh.n_active_elem();
264 
265  // The maximum number of active elements to flag for coarsening
266  const dof_id_type max_elem_coarsen =
267  static_cast<dof_id_type>(_coarsen_fraction * n_active_elem) + 1;
268 
269  // The maximum number of elements to flag for refinement
270  const dof_id_type max_elem_refine =
271  static_cast<dof_id_type>(_refine_fraction * n_active_elem) + 1;
272 
273  // Clean up the refinement flags. These could be left
274  // over from previous refinement steps.
275  this->clean_refinement_flags();
276 
277  // The target number of elements to add or remove
278  const std::ptrdiff_t n_elem_new =
279  std::ptrdiff_t(_nelem_target) - std::ptrdiff_t(n_active_elem);
280 
281  // Create an vector with active element errors and ids,
282  // sorted by highest errors first
283  const dof_id_type max_elem_id = _mesh.max_elem_id();
284  std::vector<std::pair<ErrorVectorReal, dof_id_type> > sorted_error;
285 
286  sorted_error.reserve (n_active_elem);
287 
288  // On a DistributedMesh, we need to communicate to know which remote ids
289  // correspond to active elements.
290  {
291  std::vector<bool> is_active(max_elem_id, false);
292 
293  MeshBase::element_iterator elem_it = _mesh.active_local_elements_begin();
294  const MeshBase::element_iterator elem_end = _mesh.active_local_elements_end();
295  for (; elem_it != elem_end; ++elem_it)
296  {
297  const dof_id_type eid = (*elem_it)->id();
298  is_active[eid] = true;
299  libmesh_assert_less (eid, error_per_cell.size());
300  sorted_error.push_back
301  (std::make_pair(error_per_cell[eid], eid));
302  }
303 
304  this->comm().max(is_active);
305 
306  this->comm().allgather(sorted_error);
307  }
308 
309  // Default sort works since pairs are sorted lexicographically
310  std::sort (sorted_error.begin(), sorted_error.end());
311  std::reverse (sorted_error.begin(), sorted_error.end());
312 
313  // Create a sorted error vector with coarsenable parent elements
314  // only, sorted by lowest errors first
315  ErrorVector error_per_parent;
316  std::vector<std::pair<ErrorVectorReal, dof_id_type> > sorted_parent_error;
317  Real parent_error_min, parent_error_max;
318 
319  create_parent_error_vector(error_per_cell,
320  error_per_parent,
321  parent_error_min,
322  parent_error_max);
323 
324  // create_parent_error_vector sets values for non-parents and
325  // non-coarsenable parents to -1. Get rid of them.
326  for (std::size_t i=0; i != error_per_parent.size(); ++i)
327  if (error_per_parent[i] != -1)
328  sorted_parent_error.push_back(std::make_pair(error_per_parent[i], i));
329 
330  std::sort (sorted_parent_error.begin(), sorted_parent_error.end());
331 
332  // Keep track of how many elements we plan to coarsen & refine
333  dof_id_type coarsen_count = 0;
334  dof_id_type refine_count = 0;
335 
336  const unsigned int dim = _mesh.mesh_dimension();
337  unsigned int twotodim = 1;
338  for (unsigned int i=0; i!=dim; ++i)
339  twotodim *= 2;
340 
341  // First, let's try to get our element count to target_nelem
342  if (n_elem_new >= 0)
343  {
344  // Every element refinement creates at least
345  // 2^dim-1 new elements
346  refine_count =
347  std::min(cast_int<dof_id_type>(n_elem_new / (twotodim-1)),
348  max_elem_refine);
349  }
350  else
351  {
352  // Every successful element coarsening is likely to destroy
353  // 2^dim-1 net elements.
354  coarsen_count =
355  std::min(cast_int<dof_id_type>(-n_elem_new / (twotodim-1)),
356  max_elem_coarsen);
357  }
358 
359  // Next, let's see if we can trade any refinement for coarsening
360  while (coarsen_count < max_elem_coarsen &&
361  refine_count < max_elem_refine &&
362  coarsen_count < sorted_parent_error.size() &&
363  refine_count < sorted_error.size() &&
364  sorted_error[refine_count].first >
365  sorted_parent_error[coarsen_count].first * _coarsen_threshold)
366  {
367  coarsen_count++;
368  refine_count++;
369  }
370 
371  // On a DistributedMesh, we need to communicate to know which remote ids
372  // correspond to refinable elements
373  dof_id_type successful_refine_count = 0;
374  {
375  std::vector<bool> is_refinable(max_elem_id, false);
376 
377  for (std::size_t i=0; i != sorted_error.size(); ++i)
378  {
379  dof_id_type eid = sorted_error[i].second;
380  Elem * elem = _mesh.query_elem_ptr(eid);
381  if (elem && elem->level() < _max_h_level)
382  is_refinable[eid] = true;
383  }
384  this->comm().max(is_refinable);
385 
386  if (refine_count > max_elem_refine)
387  refine_count = max_elem_refine;
388  for (std::size_t i=0; i != sorted_error.size(); ++i)
389  {
390  if (successful_refine_count >= refine_count)
391  break;
392 
393  dof_id_type eid = sorted_error[i].second;
394  Elem * elem = _mesh.query_elem_ptr(eid);
395  if (is_refinable[eid])
396  {
397  if (elem)
399  successful_refine_count++;
400  }
401  }
402  }
403 
404  // If we couldn't refine enough elements, don't coarsen too many
405  // either
406  if (coarsen_count < (refine_count - successful_refine_count))
407  coarsen_count = 0;
408  else
409  coarsen_count -= (refine_count - successful_refine_count);
410 
411  if (coarsen_count > max_elem_coarsen)
412  coarsen_count = max_elem_coarsen;
413 
414  dof_id_type successful_coarsen_count = 0;
415  if (coarsen_count)
416  {
417  for (std::size_t i=0; i != sorted_parent_error.size(); ++i)
418  {
419  if (successful_coarsen_count >= coarsen_count * twotodim)
420  break;
421 
422  dof_id_type parent_id = sorted_parent_error[i].second;
423  Elem * parent = _mesh.query_elem_ptr(parent_id);
424 
425  // On a DistributedMesh we skip remote elements
426  if (!parent)
427  continue;
428 
429  libmesh_assert(parent->has_children());
430  for (unsigned int c=0; c != parent->n_children(); ++c)
431  {
432  Elem * elem = parent->child_ptr(c);
433  if (elem && elem != remote_elem)
434  {
435  libmesh_assert(elem->active());
436  elem->set_refinement_flag(Elem::COARSEN);
437  successful_coarsen_count++;
438  }
439  }
440  }
441  }
442 
443  // Return true if we've done all the AMR/C we can
444  if (!successful_coarsen_count &&
445  !successful_refine_count)
446  return true;
447  // And false if there may still be more to do.
448  return false;
449 }
virtual dof_id_type n_active_elem() const =0
void set_refinement_flag(const RefinementState rflag)
Definition: elem.h:2228
void create_parent_error_vector(const ErrorVector &error_per_cell, ErrorVector &error_per_parent, Real &parent_error_min, Real &parent_error_max)
libmesh_assert(j)
virtual dof_id_type max_elem_id() const =0
virtual element_iterator active_local_elements_begin()=0
virtual const Elem * query_elem_ptr(const dof_id_type i) const =0
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
const Parallel::Communicator & comm() const
unsigned int mesh_dimension() const
Definition: mesh_base.C:148
virtual element_iterator active_local_elements_end()=0
long double min(long double a, double b)
uint8_t dof_id_type
Definition: id_types.h:64
void allgather(const T &send, std::vector< T > &recv) const
const RemoteElem * remote_elem
Definition: remote_elem.C:57
bool libMesh::MeshRefinement::get_enforce_mismatch_limit_prior_to_refinement ( )
inline

Returns the state of the _enforce_mismatch_limit_prior_to_refinement flag. Defaults to false. Deprecated - use enforce_mismatch_limit_prior_to_refinement() instead.

Definition at line 922 of file mesh_refinement.h.

References enforce_mismatch_limit_prior_to_refinement().

Referenced by get_mesh().

923 {
924  libmesh_deprecated();
926 }
bool & enforce_mismatch_limit_prior_to_refinement()
const MeshBase& libMesh::MeshRefinement::get_mesh ( ) const
inline
Returns
a constant reference to the MeshBase object associated with this object.

Definition at line 317 of file mesh_refinement.h.

References _mesh.

317 { return _mesh; }
bool libMesh::MeshRefinement::has_topological_neighbor ( const Elem elem,
const PointLocatorBase point_locator,
const Elem neighbor 
)
private

Local dispatch function for checking the correct has_neighbor function from the Elem class

Definition at line 1829 of file mesh_refinement.C.

References _mesh, _periodic_boundaries, libMesh::Elem::has_neighbor(), libMesh::Elem::has_topological_neighbor(), and libMesh::libmesh_assert().

Referenced by get_mesh(), make_coarsening_compatible(), and make_refinement_compatible().

1832 {
1833 #ifdef LIBMESH_ENABLE_PERIODIC
1834  if (_periodic_boundaries && !_periodic_boundaries->empty())
1835  {
1836  libmesh_assert(point_locator);
1837  return elem->has_topological_neighbor(neighbor, _mesh, *point_locator, _periodic_boundaries);
1838  }
1839 #endif
1840  return elem->has_neighbor(neighbor);
1841 }
PeriodicBoundaries * _periodic_boundaries
libmesh_assert(j)
bool libMesh::MeshRefinement::limit_level_mismatch_at_edge ( const unsigned int  max_mismatch)
private

Definition at line 138 of file mesh_refinement_smoothing.C.

References _enforce_mismatch_limit_prior_to_refinement, _mesh, libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), libMesh::Elem::build_edge_ptr(), libMesh::ParallelObject::comm(), EDGE, enforce_mismatch_limit_prior_to_refinement(), libMesh::Elem::level(), libmesh_nullptr, std::max(), libMesh::Parallel::Communicator::max(), libMesh::Elem::n_edges(), libMesh::Elem::p_level(), libMesh::Elem::p_refinement_flag(), libMesh::Elem::REFINE, libMesh::Elem::refinement_flag(), libMesh::Elem::set_p_refinement_flag(), libMesh::Elem::set_refinement_flag(), and swap().

Referenced by _smooth_flags(), and get_mesh().

139 {
140  // This function must be run on all processors at once
141  parallel_object_only();
142 
143  bool flags_changed = false;
144 
145 
146  // Maps holding the maximum element level that touches an edge
147  std::map<std::pair<unsigned int, unsigned int>, unsigned char>
148  max_level_at_edge;
149  std::map<std::pair<unsigned int, unsigned int>, unsigned char>
150  max_p_level_at_edge;
151 
152  // Loop over all the active elements & fill the maps
153  {
154  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
155  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
156 
157  for (; elem_it != elem_end; ++elem_it)
158  {
159  const Elem * elem = *elem_it;
160  const unsigned char elem_level =
161  cast_int<unsigned char>(elem->level() +
162  ((elem->refinement_flag() == Elem::REFINE) ? 1 : 0));
163  const unsigned char elem_p_level =
164  cast_int<unsigned char>(elem->p_level() +
165  ((elem->p_refinement_flag() == Elem::REFINE) ? 1 : 0));
166 
167  // Set the max_level at each edge
168  for (unsigned int n=0; n<elem->n_edges(); n++)
169  {
170  UniquePtr<const Elem> edge = elem->build_edge_ptr(n);
171  dof_id_type childnode0 = edge->node_id(0);
172  dof_id_type childnode1 = edge->node_id(1);
173  if (childnode1 < childnode0)
174  std::swap(childnode0, childnode1);
175 
176  for (const Elem * p = elem; p != libmesh_nullptr; p = p->parent())
177  {
178  UniquePtr<const Elem> pedge = p->build_edge_ptr(n);
179  dof_id_type node0 = pedge->node_id(0);
180  dof_id_type node1 = pedge->node_id(1);
181 
182  if (node1 < node0)
183  std::swap(node0, node1);
184 
185  // If elem does not share this edge with its ancestor
186  // p, refinement levels of elements sharing p's edge
187  // are not restricted by refinement levels of elem.
188  // Furthermore, elem will not share this edge with any
189  // of p's ancestors, so we can safely break out of the
190  // for loop early.
191  if (node0 != childnode0 && node1 != childnode1)
192  break;
193 
194  childnode0 = node0;
195  childnode1 = node1;
196 
197  std::pair<unsigned int, unsigned int> edge_key =
198  std::make_pair(node0, node1);
199 
200  if (max_level_at_edge.find(edge_key) ==
201  max_level_at_edge.end())
202  {
203  max_level_at_edge[edge_key] = elem_level;
204  max_p_level_at_edge[edge_key] = elem_p_level;
205  }
206  else
207  {
208  max_level_at_edge[edge_key] =
209  std::max (max_level_at_edge[edge_key], elem_level);
210  max_p_level_at_edge[edge_key] =
211  std::max (max_p_level_at_edge[edge_key], elem_p_level);
212  }
213  }
214  }
215  }
216  }
217 
218 
219  // Now loop over the active elements and flag the elements
220  // who violate the requested level mismatch
221  {
222  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
223  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
224 
225  for (; elem_it != elem_end; ++elem_it)
226  {
227  Elem * elem = *elem_it;
228  const unsigned int elem_level = elem->level();
229  const unsigned int elem_p_level = elem->p_level();
230 
231  // Skip the element if it is already fully flagged
232  if (elem->refinement_flag() == Elem::REFINE &&
233  elem->p_refinement_flag() == Elem::REFINE
235  continue;
236 
237  // Loop over the nodes, check for possible mismatch
238  for (unsigned int n=0; n<elem->n_edges(); n++)
239  {
240  UniquePtr<Elem> edge = elem->build_edge_ptr(n);
241  dof_id_type node0 = edge->node_id(0);
242  dof_id_type node1 = edge->node_id(1);
243  if (node1 < node0)
244  std::swap(node0, node1);
245 
246  std::pair<dof_id_type, dof_id_type> edge_key =
247  std::make_pair(node0, node1);
248 
249  // Flag the element for refinement if it violates
250  // the requested level mismatch
251  if ((elem_level + max_mismatch) < max_level_at_edge[edge_key]
252  && elem->refinement_flag() != Elem::REFINE)
253  {
254  elem->set_refinement_flag (Elem::REFINE);
255  flags_changed = true;
256  }
257 
258  if ((elem_p_level + max_mismatch) < max_p_level_at_edge[edge_key]
259  && elem->p_refinement_flag() != Elem::REFINE)
260  {
261  elem->set_p_refinement_flag (Elem::REFINE);
262  flags_changed = true;
263  }
264 
265  // Possibly enforce limit mismatch prior to refinement
266  flags_changed |= this->enforce_mismatch_limit_prior_to_refinement(elem, EDGE, max_mismatch);
267  } // loop over edges
268  } // loop over active elements
269  }
270 
271  // If flags changed on any processor then they changed globally
272  this->comm().max(flags_changed);
273 
274  return flags_changed;
275 }
bool & enforce_mismatch_limit_prior_to_refinement()
const class libmesh_nullptr_t libmesh_nullptr
long double max(long double a, double b)
bool _enforce_mismatch_limit_prior_to_refinement
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
const Parallel::Communicator & comm() const
void swap(Iterator &lhs, Iterator &rhs)
uint8_t dof_id_type
Definition: id_types.h:64
bool libMesh::MeshRefinement::limit_level_mismatch_at_node ( const unsigned int  max_mismatch)
private

This algorithm restricts the maximum level mismatch at any node in the mesh. Calling this with max_mismatch equal to 1 would transform this mesh:

* o---o---o---o---o-------o-------o
* |   |   |   |   |       |       |
* |   |   |   |   |       |       |
* o---o---o---o---o       |       |
* |   |   |   |   |       |       |
* |   |   |   |   |       |       |
* o---o---o---o---o-------o-------o
* |   |   |   |   |       |       |
* |   |   |   |   |       |       |
* o---o---o---o---o       |       |
* |   |   |   |   |       |       |
* |   |   |   |   |       |       |
* o---o---o---o---o-------o-------o
* |       |       |               |
* |       |       |               |
* |       |       |               |
* |       |       |               |
* |       |       |               |
* o-------o-------o               |
* |       |       |               |
* |       |       |               |
* |       |       |               |
* |       |       |               |
* |       |       |               |
* o-------o-------o---------------o
* 

into this:

* o---o---o---o---o-------o-------o
* |   |   |   |   |       |       |
* |   |   |   |   |       |       |
* o---o---o---o---o       |       |
* |   |   |   |   |       |       |
* |   |   |   |   |       |       |
* o---o---o---o---o-------o-------o
* |   |   |   |   |       |       |
* |   |   |   |   |       |       |
* o---o---o---o---o       |       |
* |   |   |   |   |       |       |
* |   |   |   |   |       |       |
* o---o---o---o---o-------o-------o
* |       |       |       :       |
* |       |       |       :       |
* |       |       |       :       |
* |       |       |       :       |
* |       |       |       :       |
* o-------o-------o.......o.......o
* |       |       |       :       |
* |       |       |       :       |
* |       |       |       :       |
* |       |       |       :       |
* |       |       |       :       |
* o-------o-------o-------o-------o
* 

by refining the indicated element

Definition at line 39 of file mesh_refinement_smoothing.C.

References _enforce_mismatch_limit_prior_to_refinement, _mesh, libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), libMesh::ParallelObject::comm(), enforce_mismatch_limit_prior_to_refinement(), libMesh::Elem::level(), std::max(), libMesh::Parallel::Communicator::max(), libMesh::MeshBase::n_nodes(), libMesh::Elem::n_nodes(), libMesh::Elem::node_id(), libMesh::Elem::p_level(), libMesh::Elem::p_refinement_flag(), POINT, libMesh::Elem::REFINE, libMesh::Elem::refinement_flag(), libMesh::Elem::set_p_refinement_flag(), and libMesh::Elem::set_refinement_flag().

Referenced by _smooth_flags(), and get_mesh().

40 {
41  // This function must be run on all processors at once
42  parallel_object_only();
43 
44  bool flags_changed = false;
45 
46 
47  // Vector holding the maximum element level that touches a node.
48  std::vector<unsigned char> max_level_at_node (_mesh.n_nodes(), 0);
49  std::vector<unsigned char> max_p_level_at_node (_mesh.n_nodes(), 0);
50 
51  // Loop over all the active elements & fill the vector
52  {
53  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
54  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
55 
56  for (; elem_it != elem_end; ++elem_it)
57  {
58  const Elem * elem = *elem_it;
59  const unsigned char elem_level =
60  cast_int<unsigned char>(elem->level() +
61  ((elem->refinement_flag() == Elem::REFINE) ? 1 : 0));
62  const unsigned char elem_p_level =
63  cast_int<unsigned char>(elem->p_level() +
64  ((elem->p_refinement_flag() == Elem::REFINE) ? 1 : 0));
65 
66  // Set the max_level at each node
67  for (unsigned int n=0; n<elem->n_nodes(); n++)
68  {
69  const dof_id_type node_number = elem->node_id(n);
70 
71  libmesh_assert_less (node_number, max_level_at_node.size());
72 
73  max_level_at_node[node_number] =
74  std::max (max_level_at_node[node_number], elem_level);
75  max_p_level_at_node[node_number] =
76  std::max (max_p_level_at_node[node_number], elem_p_level);
77  }
78  }
79  }
80 
81 
82  // Now loop over the active elements and flag the elements
83  // who violate the requested level mismatch. Alternatively, if
84  // _enforce_mismatch_limit_prior_to_refinement is true, swap refinement flags
85  // accordingly.
86  {
87  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
88  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
89 
90  for (; elem_it != elem_end; ++elem_it)
91  {
92  Elem * elem = *elem_it;
93  const unsigned int elem_level = elem->level();
94  const unsigned int elem_p_level = elem->p_level();
95 
96  // Skip the element if it is already fully flagged
97  // unless we are enforcing mismatch prior to refienemnt and may need to
98  // remove the refinement flag(s)
99  if (elem->refinement_flag() == Elem::REFINE &&
100  elem->p_refinement_flag() == Elem::REFINE
102  continue;
103 
104  // Loop over the nodes, check for possible mismatch
105  for (unsigned int n=0; n<elem->n_nodes(); n++)
106  {
107  const dof_id_type node_number = elem->node_id(n);
108 
109  // Flag the element for refinement if it violates
110  // the requested level mismatch
111  if ((elem_level + max_mismatch) < max_level_at_node[node_number]
112  && elem->refinement_flag() != Elem::REFINE)
113  {
114  elem->set_refinement_flag (Elem::REFINE);
115  flags_changed = true;
116  }
117  if ((elem_p_level + max_mismatch) < max_p_level_at_node[node_number]
118  && elem->p_refinement_flag() != Elem::REFINE)
119  {
120  elem->set_p_refinement_flag (Elem::REFINE);
121  flags_changed = true;
122  }
123 
124  // Possibly enforce limit mismatch prior to refinement
125  flags_changed |= this->enforce_mismatch_limit_prior_to_refinement(elem, POINT, max_mismatch);
126  }
127  }
128  }
129 
130  // If flags changed on any processor then they changed globally
131  this->comm().max(flags_changed);
132 
133  return flags_changed;
134 }
bool & enforce_mismatch_limit_prior_to_refinement()
long double max(long double a, double b)
bool _enforce_mismatch_limit_prior_to_refinement
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
const Parallel::Communicator & comm() const
virtual dof_id_type n_nodes() const =0
uint8_t dof_id_type
Definition: id_types.h:64
bool libMesh::MeshRefinement::limit_overrefined_boundary ( const signed char  max_mismatch)
private

Definition at line 279 of file mesh_refinement_smoothing.C.

References _mesh, libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), libMesh::ParallelObject::comm(), libMesh::Elem::dim(), libMesh::Elem::find_interior_neighbors(), libMesh::Elem::interior_parent(), libMesh::Elem::level(), libMesh::Parallel::Communicator::max(), libMesh::Elem::p_level(), libMesh::Elem::p_refinement_flag(), libMesh::Elem::REFINE, libMesh::Elem::refinement_flag(), libMesh::Elem::set_p_refinement_flag(), and libMesh::Elem::set_refinement_flag().

Referenced by _smooth_flags(), and get_mesh().

280 {
281  // This function must be run on all processors at once
282  parallel_object_only();
283 
284  bool flags_changed = false;
285 
286  // Loop over all the active elements & look for mismatches to fix.
287  {
288  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
289  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
290 
291  for (; elem_it != elem_end; ++elem_it)
292  {
293  Elem * elem = *elem_it;
294 
295  // If we don't have an interior_parent then there's nothing to
296  // be mismatched with.
297  if ((elem->dim() >= LIBMESH_DIM) ||
298  !elem->interior_parent())
299  continue;
300 
301  const unsigned char elem_level =
302  cast_int<unsigned char>(elem->level() +
303  ((elem->refinement_flag() == Elem::REFINE) ? 1 : 0));
304  const unsigned char elem_p_level =
305  cast_int<unsigned char>(elem->p_level() +
306  ((elem->p_refinement_flag() == Elem::REFINE) ? 1 : 0));
307 
308  // get all relevant interior elements
309  std::set<const Elem *> neighbor_set;
310  elem->find_interior_neighbors(neighbor_set);
311 
312  std::set<const Elem *>::iterator n_it = neighbor_set.begin();
313  for (; n_it != neighbor_set.end(); ++n_it)
314  {
315  // FIXME - non-const versions of the Elem set methods
316  // would be nice
317  Elem * neighbor = const_cast<Elem *>(*n_it);
318 
319  if (max_mismatch >= 0)
320  {
321  if ((elem_level > neighbor->level() + max_mismatch) &&
322  (neighbor->refinement_flag() != Elem::REFINE))
323  {
324  neighbor->set_refinement_flag(Elem::REFINE);
325  flags_changed = true;
326  }
327 
328  if ((elem_p_level > neighbor->p_level() + max_mismatch) &&
329  (neighbor->p_refinement_flag() != Elem::REFINE))
330  {
331  neighbor->set_p_refinement_flag(Elem::REFINE);
332  flags_changed = true;
333  }
334  }
335  } // loop over interior neighbors
336  }
337  }
338 
339  // If flags changed on any processor then they changed globally
340  this->comm().max(flags_changed);
341 
342  return flags_changed;
343 }
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
const Parallel::Communicator & comm() const
bool libMesh::MeshRefinement::limit_underrefined_boundary ( const signed char  max_mismatch)
private

Definition at line 347 of file mesh_refinement_smoothing.C.

References _mesh, libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), libMesh::ParallelObject::comm(), libMesh::Elem::dim(), libMesh::Elem::find_interior_neighbors(), libMesh::Elem::interior_parent(), libMesh::Elem::level(), libMesh::Parallel::Communicator::max(), libMesh::Elem::p_level(), libMesh::Elem::p_refinement_flag(), libMesh::Elem::REFINE, libMesh::Elem::refinement_flag(), libMesh::Elem::set_p_refinement_flag(), and libMesh::Elem::set_refinement_flag().

Referenced by _smooth_flags(), and get_mesh().

348 {
349  // This function must be run on all processors at once
350  parallel_object_only();
351 
352  bool flags_changed = false;
353 
354  // Loop over all the active elements & look for mismatches to fix.
355  {
356  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
357  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
358 
359  for (; elem_it != elem_end; ++elem_it)
360  {
361  Elem * elem = *elem_it;
362 
363  // If we don't have an interior_parent then there's nothing to
364  // be mismatched with.
365  if ((elem->dim() >= LIBMESH_DIM) ||
366  !elem->interior_parent())
367  continue;
368 
369  // get all relevant interior elements
370  std::set<const Elem *> neighbor_set;
371  elem->find_interior_neighbors(neighbor_set);
372 
373  std::set<const Elem *>::iterator n_it = neighbor_set.begin();
374  for (; n_it != neighbor_set.end(); ++n_it)
375  {
376  // FIXME - non-const versions of the Elem set methods
377  // would be nice
378  const Elem * neighbor = *n_it;
379 
380  const unsigned char neighbor_level =
381  cast_int<unsigned char>(neighbor->level() +
382  ((neighbor->refinement_flag() == Elem::REFINE) ? 1 : 0));
383 
384  const unsigned char neighbor_p_level =
385  cast_int<unsigned char>(neighbor->p_level() +
386  ((neighbor->p_refinement_flag() == Elem::REFINE) ? 1 : 0));
387 
388  if (max_mismatch >= 0)
389  {
390  if ((neighbor_level >
391  elem->level() + max_mismatch) &&
392  (elem->refinement_flag() != Elem::REFINE))
393  {
394  elem->set_refinement_flag(Elem::REFINE);
395  flags_changed = true;
396  }
397 
398  if ((neighbor_p_level >
399  elem->p_level() + max_mismatch) &&
400  (elem->p_refinement_flag() != Elem::REFINE))
401  {
402  elem->set_p_refinement_flag(Elem::REFINE);
403  flags_changed = true;
404  }
405  }
406  } // loop over interior neighbors
407  }
408  }
409 
410  // If flags changed on any processor then they changed globally
411  this->comm().max(flags_changed);
412 
413  return flags_changed;
414 }
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
const Parallel::Communicator & comm() const
bool libMesh::MeshRefinement::make_coarsening_compatible ( )
private

Take user-specified coarsening flags and augment them so that level-one dependency is satisfied.

This function used to take an argument, maintain_level_one - new code should use face_level_mismatch_limit() instead.

Definition at line 855 of file mesh_refinement.C.

References _face_level_mismatch_limit, _mesh, _periodic_boundaries, libMesh::Elem::active(), libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), libMesh::Elem::ancestor(), libMesh::Elem::child_ptr(), libMesh::Elem::COARSEN, libMesh::Elem::COARSEN_INACTIVE, libMesh::ParallelObject::comm(), libMesh::Elem::DO_NOTHING, libMesh::MeshBase::elements_begin(), libMesh::MeshBase::elements_end(), libMesh::Elem::has_children(), has_topological_neighbor(), libMesh::Elem::INACTIVE, libMesh::MeshBase::is_serial(), libMesh::Elem::level(), libMesh::MeshBase::level_elements_begin(), libMesh::MeshBase::level_elements_end(), libMesh::libmesh_assert(), libmesh_nullptr, std::max(), libMesh::MeshTools::max_level(), libMesh::Parallel::Communicator::min(), libMesh::Elem::n_children(), libMesh::Elem::n_neighbors(), libMesh::Elem::p_level(), libMesh::Elem::p_refinement_flag(), libMesh::ParallelObject::processor_id(), libMesh::DofObject::processor_id(), libMesh::Elem::REFINE, libMesh::Elem::refinement_flag(), libMesh::remote_elem, libMesh::Elem::set_p_refinement_flag(), libMesh::Elem::set_refinement_flag(), libMesh::MeshBase::sub_point_locator(), topological_neighbor(), and libMesh::Parallel::verify().

Referenced by _smooth_flags(), coarsen_elements(), get_mesh(), and refine_and_coarsen_elements().

856 {
857  // This function must be run on all processors at once
858  parallel_object_only();
859 
860  // We may need a PointLocator for topological_neighbor() tests
861  // later, which we need to make sure gets constructed on all
862  // processors at once.
863  UniquePtr<PointLocatorBase> point_locator;
864 
865 #ifdef LIBMESH_ENABLE_PERIODIC
866  bool has_periodic_boundaries =
868  libmesh_assert(this->comm().verify(has_periodic_boundaries));
869 
870  if (has_periodic_boundaries)
871  point_locator = _mesh.sub_point_locator();
872 #endif
873 
874  LOG_SCOPE ("make_coarsening_compatible()", "MeshRefinement");
875 
876  // Unless we encounter a specific situation level-one
877  // will be satisfied after executing this loop just once
878  bool level_one_satisfied = true;
879 
880 
881  // Unless we encounter a specific situation we will be compatible
882  // with any selected refinement flags
883  bool compatible_with_refinement = true;
884 
885 
886  // find the maximum h and p levels in the mesh
887  unsigned int max_level = 0;
888  unsigned int max_p_level = 0;
889 
890  {
891  // First we look at all the active level-0 elements. Since it doesn't make
892  // sense to coarsen them we must un-set their coarsen flags if
893  // they are set.
894  MeshBase::element_iterator el = _mesh.active_elements_begin();
895  const MeshBase::element_iterator end_el = _mesh.active_elements_end();
896 
897  for (; el != end_el; ++el)
898  {
899  Elem * elem = *el;
900  max_level = std::max(max_level, elem->level());
901  max_p_level =
902  std::max(max_p_level,
903  static_cast<unsigned int>(elem->p_level()));
904 
905  if ((elem->level() == 0) &&
906  (elem->refinement_flag() == Elem::COARSEN))
907  elem->set_refinement_flag(Elem::DO_NOTHING);
908 
909  if ((elem->p_level() == 0) &&
910  (elem->p_refinement_flag() == Elem::COARSEN))
911  elem->set_p_refinement_flag(Elem::DO_NOTHING);
912  }
913  }
914 
915  // if there are no refined elements on this processor then
916  // there is no work for us to do
917  if (max_level == 0 && max_p_level == 0)
918  {
919  // But we still have to check with other processors
920  this->comm().min(compatible_with_refinement);
921 
922  return compatible_with_refinement;
923  }
924 
925 
926 
927  // Loop over all the active elements. If an element is marked
928  // for coarsening we better check its neighbors. If ANY of these neighbors
929  // are marked for refinement AND are at the same level then there is a
930  // conflict. By convention refinement wins, so we un-mark the element for
931  // coarsening. Level-one would be violated in this case so we need to re-run
932  // the loop.
934  {
935 
936  repeat:
937  level_one_satisfied = true;
938 
939  do
940  {
941  level_one_satisfied = true;
942 
943  MeshBase::element_iterator el = _mesh.active_elements_begin();
944  const MeshBase::element_iterator end_el = _mesh.active_elements_end();
945 
946  for (; el != end_el; ++el)
947  {
948  Elem * elem = *el;
949  bool my_flag_changed = false;
950 
951  if (elem->refinement_flag() == Elem::COARSEN) // If the element is active and
952  // the coarsen flag is set
953  {
954  const unsigned int my_level = elem->level();
955 
956  for (unsigned int n=0; n<elem->n_neighbors(); n++)
957  {
958  const Elem * neighbor =
959  topological_neighbor(elem, point_locator.get(), n);
960 
961  if (neighbor != libmesh_nullptr && // I have a
962  neighbor != remote_elem) // neighbor here
963  {
964  if (neighbor->active()) // and it is active
965  {
966  if ((neighbor->level() == my_level) &&
967  (neighbor->refinement_flag() == Elem::REFINE)) // the neighbor is at my level
968  // and wants to be refined
969  {
971  my_flag_changed = true;
972  break;
973  }
974  }
975  else // I have a neighbor and it is not active. That means it has children.
976  { // While it _may_ be possible to coarsen us if all the children of
977  // that element want to be coarsened, it is impossible to know at this
978  // stage. Forget about it for the moment... This can be handled in
979  // two steps.
980  elem->set_refinement_flag(Elem::DO_NOTHING);
981  my_flag_changed = true;
982  break;
983  }
984  }
985  }
986  }
987  if (elem->p_refinement_flag() == Elem::COARSEN) // If
988  // the element is active and the order reduction flag is set
989  {
990  const unsigned int my_p_level = elem->p_level();
991 
992  for (unsigned int n=0; n<elem->n_neighbors(); n++)
993  {
994  const Elem * neighbor =
995  topological_neighbor(elem, point_locator.get(), n);
996 
997  if (neighbor != libmesh_nullptr && // I have a
998  neighbor != remote_elem) // neighbor here
999  {
1000  if (neighbor->active()) // and it is active
1001  {
1002  if ((neighbor->p_level() > my_p_level &&
1003  neighbor->p_refinement_flag() != Elem::COARSEN)
1004  || (neighbor->p_level() == my_p_level &&
1005  neighbor->p_refinement_flag() == Elem::REFINE))
1006  {
1008  my_flag_changed = true;
1009  break;
1010  }
1011  }
1012  else // I have a neighbor and it is not active.
1013  { // We need to find which of its children
1014  // have me as a neighbor, and maintain
1015  // level one p compatibility with them.
1016  // Because we currently have level one h
1017  // compatibility, we don't need to check
1018  // grandchildren
1019 
1020  libmesh_assert(neighbor->has_children());
1021  for (unsigned int c=0; c!=neighbor->n_children(); c++)
1022  {
1023  const Elem * subneighbor = neighbor->child_ptr(c);
1024  if (subneighbor != remote_elem &&
1025  subneighbor->active() &&
1026  has_topological_neighbor(subneighbor, point_locator.get(), elem))
1027  if ((subneighbor->p_level() > my_p_level &&
1028  subneighbor->p_refinement_flag() != Elem::COARSEN)
1029  || (subneighbor->p_level() == my_p_level &&
1030  subneighbor->p_refinement_flag() == Elem::REFINE))
1031  {
1032  elem->set_p_refinement_flag(Elem::DO_NOTHING);
1033  my_flag_changed = true;
1034  break;
1035  }
1036  }
1037  if (my_flag_changed)
1038  break;
1039  }
1040  }
1041  }
1042  }
1043 
1044  // If the current element's flag changed, we hadn't
1045  // satisfied the level one rule.
1046  if (my_flag_changed)
1047  level_one_satisfied = false;
1048 
1049  // Additionally, if it has non-local neighbors, and
1050  // we're not in serial, then we'll eventually have to
1051  // return compatible_with_refinement = false, because
1052  // our change has to propagate to neighboring
1053  // processors.
1054  if (my_flag_changed && !_mesh.is_serial())
1055  for (unsigned int n=0; n != elem->n_neighbors(); ++n)
1056  {
1057  Elem * neigh =
1058  topological_neighbor(elem, point_locator.get(), n);
1059 
1060  if (!neigh)
1061  continue;
1062  if (neigh == remote_elem ||
1063  neigh->processor_id() !=
1064  this->processor_id())
1065  {
1066  compatible_with_refinement = false;
1067  break;
1068  }
1069  // FIXME - for non-level one meshes we should
1070  // test all descendants
1071  if (neigh->has_children())
1072  for (unsigned int c=0; c != neigh->n_children(); ++c)
1073  if (neigh->child_ptr(c) == remote_elem ||
1074  neigh->child_ptr(c)->processor_id() !=
1075  this->processor_id())
1076  {
1077  compatible_with_refinement = false;
1078  break;
1079  }
1080  }
1081  }
1082  }
1083  while (!level_one_satisfied);
1084 
1085  } // end if (_face_level_mismatch_limit)
1086 
1087 
1088  // Next we look at all of the ancestor cells.
1089  // If there is a parent cell with all of its children
1090  // wanting to be unrefined then the element is a candidate
1091  // for unrefinement. If all the children don't
1092  // all want to be unrefined then ALL of them need to have their
1093  // unrefinement flags cleared.
1094  for (int level=(max_level); level >= 0; level--)
1095  {
1096  MeshBase::element_iterator el = _mesh.level_elements_begin(level);
1097  const MeshBase::element_iterator end_el = _mesh.level_elements_end(level);
1098  for (; el != end_el; ++el)
1099  {
1100  Elem * elem = *el;
1101  if (elem->ancestor())
1102  {
1103 
1104  // right now the element hasn't been disqualified
1105  // as a candidate for unrefinement
1106  bool is_a_candidate = true;
1107  bool found_remote_child = false;
1108 
1109  for (unsigned int c=0; c<elem->n_children(); c++)
1110  {
1111  Elem * child = elem->child_ptr(c);
1112  if (child == remote_elem)
1113  found_remote_child = true;
1114  else if ((child->refinement_flag() != Elem::COARSEN) ||
1115  !child->active() )
1116  is_a_candidate = false;
1117  }
1118 
1119  if (!is_a_candidate && !found_remote_child)
1120  {
1121  elem->set_refinement_flag(Elem::INACTIVE);
1122 
1123  for (unsigned int c=0; c<elem->n_children(); c++)
1124  {
1125  Elem * child = elem->child_ptr(c);
1126  if (child == remote_elem)
1127  continue;
1128  if (child->refinement_flag() == Elem::COARSEN)
1129  {
1130  level_one_satisfied = false;
1131  child->set_refinement_flag(Elem::DO_NOTHING);
1132  }
1133  }
1134  }
1135  }
1136  }
1137  }
1138 
1139  if (!level_one_satisfied && _face_level_mismatch_limit) goto repeat;
1140 
1141 
1142  // If all the children of a parent are set to be coarsened
1143  // then flag the parent so that they can kill their kids...
1144  MeshBase::element_iterator all_el = _mesh.elements_begin();
1145  const MeshBase::element_iterator all_el_end = _mesh.elements_end();
1146  for (; all_el != all_el_end; ++all_el)
1147  {
1148  Elem * elem = *all_el;
1149  if (elem->ancestor())
1150  {
1151 
1152  // Presume all the children are local and flagged for
1153  // coarsening and then look for a contradiction
1154  bool all_children_flagged_for_coarsening = true;
1155  bool found_remote_child = false;
1156 
1157  for (unsigned int c=0; c<elem->n_children(); c++)
1158  {
1159  Elem * child = elem->child_ptr(c);
1160  if (child == remote_elem)
1161  found_remote_child = true;
1162  else if (child->refinement_flag() != Elem::COARSEN)
1163  all_children_flagged_for_coarsening = false;
1164  }
1165 
1166  if (!found_remote_child &&
1167  all_children_flagged_for_coarsening)
1168  elem->set_refinement_flag(Elem::COARSEN_INACTIVE);
1169  else if (!found_remote_child)
1170  elem->set_refinement_flag(Elem::INACTIVE);
1171  }
1172  }
1173 
1174  // If one processor finds an incompatibility, we're globally
1175  // incompatible
1176  this->comm().min(compatible_with_refinement);
1177 
1178  return compatible_with_refinement;
1179 }
virtual bool is_serial() const
Definition: mesh_base.h:134
bool active() const
Definition: elem.h:1984
virtual element_iterator level_elements_begin(unsigned int level)=0
const class libmesh_nullptr_t libmesh_nullptr
void set_refinement_flag(const RefinementState rflag)
Definition: elem.h:2228
long double max(long double a, double b)
PeriodicBoundaries * _periodic_boundaries
unsigned int max_level(const MeshBase &mesh)
libmesh_assert(j)
virtual element_iterator elements_begin()=0
virtual element_iterator level_elements_end(unsigned int level)=0
unsigned char _face_level_mismatch_limit
virtual element_iterator elements_end()=0
const Elem * child_ptr(unsigned int i) const
Definition: elem.h:2163
bool has_topological_neighbor(const Elem *elem, const PointLocatorBase *point_locator, const Elem *neighbor)
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
bool verify(const T &r, const Communicator &comm=Communicator_World)
const Parallel::Communicator & comm() const
void set_p_refinement_flag(const RefinementState pflag)
Definition: elem.h:2244
Elem * topological_neighbor(Elem *elem, const PointLocatorBase *point_locator, const unsigned int side)
UniquePtr< PointLocatorBase > sub_point_locator() const
Definition: mesh_base.C:531
processor_id_type processor_id() const
processor_id_type processor_id() const
Definition: dof_object.h:686
const RemoteElem * remote_elem
Definition: remote_elem.C:57
bool libMesh::MeshRefinement::make_flags_parallel_consistent ( )

Copy refinement flags on ghost elements from their local processors. Return true if any flags changed.

Definition at line 827 of file mesh_refinement.C.

References _mesh, libMesh::ParallelObject::comm(), libMesh::MeshBase::elements_begin(), libMesh::MeshBase::elements_end(), libMesh::Parallel::Communicator::min(), libMesh::Elem::p_refinement_flag(), parallel_consistent, libMesh::Elem::refinement_flag(), libMesh::Elem::set_p_refinement_flag(), libMesh::Elem::set_refinement_flag(), and libMesh::Parallel::sync_dofobject_data_by_id().

Referenced by _smooth_flags(), coarsen_elements(), get_mesh(), refine_and_coarsen_elements(), and refine_elements().

828 {
829  // This function must be run on all processors at once
830  parallel_object_only();
831 
832  LOG_SCOPE ("make_flags_parallel_consistent()", "MeshRefinement");
833 
834  SyncRefinementFlags hsync(_mesh, &Elem::refinement_flag,
837  (this->comm(), _mesh.elements_begin(), _mesh.elements_end(), hsync);
838 
839  SyncRefinementFlags psync(_mesh, &Elem::p_refinement_flag,
842  (this->comm(), _mesh.elements_begin(), _mesh.elements_end(), psync);
843 
844  // If we weren't consistent in both h and p on every processor then
845  // we weren't globally consistent
846  bool parallel_consistent = hsync.parallel_consistent &&
847  psync.parallel_consistent;
848  this->comm().min(parallel_consistent);
849 
850  return parallel_consistent;
851 }
bool parallel_consistent
void set_refinement_flag(const RefinementState rflag)
Definition: elem.h:2228
virtual element_iterator elements_begin()=0
virtual element_iterator elements_end()=0
RefinementState p_refinement_flag() const
Definition: elem.h:2236
void sync_dofobject_data_by_id(const Communicator &comm, const Iterator &range_begin, const Iterator &range_end, SyncFunctor &sync)
const Parallel::Communicator & comm() const
RefinementState refinement_flag() const
Definition: elem.h:2220
void set_p_refinement_flag(const RefinementState pflag)
Definition: elem.h:2244
bool libMesh::MeshRefinement::make_refinement_compatible ( )
private

Take user-specified refinement flags and augment them so that level-one dependency is satisfied.

This function used to take an argument, maintain_level_one - new code should use face_level_mismatch_limit() instead.

Definition at line 1188 of file mesh_refinement.C.

References _face_level_mismatch_limit, _mesh, _periodic_boundaries, libMesh::Elem::active(), libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), libMesh::Elem::child_ptr(), libMesh::Elem::COARSEN, libMesh::ParallelObject::comm(), libMesh::Elem::DO_NOTHING, libMesh::Elem::has_children(), has_topological_neighbor(), libMesh::Elem::INACTIVE, libMesh::Elem::level(), libMesh::libmesh_assert(), libmesh_nullptr, libMesh::Parallel::Communicator::min(), libMesh::Elem::n_children(), libMesh::Elem::n_sides(), libMesh::Elem::p_level(), libMesh::Elem::p_refinement_flag(), libMesh::Elem::parent(), libMesh::Elem::REFINE, libMesh::Elem::refinement_flag(), libMesh::remote_elem, libMesh::Elem::set_p_refinement_flag(), libMesh::Elem::set_refinement_flag(), side, libMesh::MeshBase::sub_point_locator(), topological_neighbor(), and libMesh::Parallel::verify().

Referenced by _smooth_flags(), get_mesh(), refine_and_coarsen_elements(), and refine_elements().

1189 {
1190  // This function must be run on all processors at once
1191  parallel_object_only();
1192 
1193  // We may need a PointLocator for topological_neighbor() tests
1194  // later, which we need to make sure gets constructed on all
1195  // processors at once.
1196  UniquePtr<PointLocatorBase> point_locator;
1197 
1198 #ifdef LIBMESH_ENABLE_PERIODIC
1199  bool has_periodic_boundaries =
1201  libmesh_assert(this->comm().verify(has_periodic_boundaries));
1202 
1203  if (has_periodic_boundaries)
1204  point_locator = _mesh.sub_point_locator();
1205 #endif
1206 
1207  LOG_SCOPE ("make_refinement_compatible()", "MeshRefinement");
1208 
1209  // Unless we encounter a specific situation we will be compatible
1210  // with any selected coarsening flags
1211  bool compatible_with_coarsening = true;
1212 
1213  // This loop enforces the level-1 rule. We should only
1214  // execute it if the user indeed wants level-1 satisfied!
1216  {
1217  // Unless we encounter a specific situation level-one
1218  // will be satisfied after executing this loop just once
1219  bool level_one_satisfied = true;
1220 
1221  do
1222  {
1223  level_one_satisfied = true;
1224 
1225  MeshBase::element_iterator el = _mesh.active_elements_begin();
1226  const MeshBase::element_iterator end_el = _mesh.active_elements_end();
1227 
1228  for (; el != end_el; ++el)
1229  {
1230  Elem * elem = *el;
1231  if (elem->refinement_flag() == Elem::REFINE) // If the element is active and the
1232  // h refinement flag is set
1233  {
1234  const unsigned int my_level = elem->level();
1235 
1236  for (unsigned int side=0; side != elem->n_sides(); side++)
1237  {
1238  Elem * neighbor =
1239  topological_neighbor(elem, point_locator.get(), side);
1240 
1241  if (neighbor != libmesh_nullptr && // I have a
1242  neighbor != remote_elem && // neighbor here
1243  neighbor->active()) // and it is active
1244  {
1245  // Case 1: The neighbor is at the same level I am.
1246  // 1a: The neighbor will be refined -> NO PROBLEM
1247  // 1b: The neighbor won't be refined -> NO PROBLEM
1248  // 1c: The neighbor wants to be coarsened -> PROBLEM
1249  if (neighbor->level() == my_level)
1250  {
1251  if (neighbor->refinement_flag() == Elem::COARSEN)
1252  {
1254  if (neighbor->parent())
1255  neighbor->parent()->set_refinement_flag(Elem::INACTIVE);
1256  compatible_with_coarsening = false;
1257  level_one_satisfied = false;
1258  }
1259  }
1260 
1261 
1262  // Case 2: The neighbor is one level lower than I am.
1263  // The neighbor thus MUST be refined to satisfy
1264  // the level-one rule, regardless of whether it
1265  // was originally flagged for refinement. If it
1266  // wasn't flagged already we need to repeat
1267  // this process.
1268  else if ((neighbor->level()+1) == my_level)
1269  {
1270  if (neighbor->refinement_flag() != Elem::REFINE)
1271  {
1272  neighbor->set_refinement_flag(Elem::REFINE);
1273  if (neighbor->parent())
1274  neighbor->parent()->set_refinement_flag(Elem::INACTIVE);
1275  compatible_with_coarsening = false;
1276  level_one_satisfied = false;
1277  }
1278  }
1279 #ifdef DEBUG
1280  // Note that the only other possibility is that the
1281  // neighbor is already refined, in which case it isn't
1282  // active and we should never get here.
1283  else
1284  libmesh_error_msg("ERROR: Neighbor level must be equal or 1 higher than mine.");
1285 #endif
1286  }
1287  }
1288  }
1289  if (elem->p_refinement_flag() == Elem::REFINE) // If the element is active and the
1290  // p refinement flag is set
1291  {
1292  const unsigned int my_p_level = elem->p_level();
1293 
1294  for (unsigned int side=0; side != elem->n_sides(); side++)
1295  {
1296  Elem * neighbor =
1297  topological_neighbor(elem, point_locator.get(), side);
1298 
1299  if (neighbor != libmesh_nullptr && // I have a
1300  neighbor != remote_elem) // neighbor here
1301  {
1302  if (neighbor->active()) // and it is active
1303  {
1304  if (neighbor->p_level() < my_p_level &&
1305  neighbor->p_refinement_flag() != Elem::REFINE)
1306  {
1308  level_one_satisfied = false;
1309  compatible_with_coarsening = false;
1310  }
1311  if (neighbor->p_level() == my_p_level &&
1312  neighbor->p_refinement_flag() == Elem::COARSEN)
1313  {
1314  neighbor->set_p_refinement_flag(Elem::DO_NOTHING);
1315  level_one_satisfied = false;
1316  compatible_with_coarsening = false;
1317  }
1318  }
1319  else // I have an inactive neighbor
1320  {
1321  libmesh_assert(neighbor->has_children());
1322  for (unsigned int c=0; c!=neighbor->n_children(); c++)
1323  {
1324  Elem * subneighbor = neighbor->child_ptr(c);
1325  if (subneighbor == remote_elem)
1326  continue;
1327  if (subneighbor->active() &&
1328  has_topological_neighbor(subneighbor, point_locator.get(), elem))
1329  {
1330  if (subneighbor->p_level() < my_p_level &&
1331  subneighbor->p_refinement_flag() != Elem::REFINE)
1332  {
1333  // We should already be level one
1334  // compatible
1335  libmesh_assert_greater (subneighbor->p_level() + 2u,
1336  my_p_level);
1337  subneighbor->set_p_refinement_flag(Elem::REFINE);
1338  level_one_satisfied = false;
1339  compatible_with_coarsening = false;
1340  }
1341  if (subneighbor->p_level() == my_p_level &&
1342  subneighbor->p_refinement_flag() == Elem::COARSEN)
1343  {
1344  subneighbor->set_p_refinement_flag(Elem::DO_NOTHING);
1345  level_one_satisfied = false;
1346  compatible_with_coarsening = false;
1347  }
1348  }
1349  }
1350  }
1351  }
1352  }
1353  }
1354  }
1355  }
1356 
1357  while (!level_one_satisfied);
1358  } // end if (_face_level_mismatch_limit)
1359 
1360  // If we're not compatible on one processor, we're globally not
1361  // compatible
1362  this->comm().min(compatible_with_coarsening);
1363 
1364  return compatible_with_coarsening;
1365 }
bool active() const
Definition: elem.h:1984
unsigned short int side
Definition: xdr_io.C:49
const class libmesh_nullptr_t libmesh_nullptr
void set_refinement_flag(const RefinementState rflag)
Definition: elem.h:2228
PeriodicBoundaries * _periodic_boundaries
libmesh_assert(j)
unsigned char _face_level_mismatch_limit
bool has_topological_neighbor(const Elem *elem, const PointLocatorBase *point_locator, const Elem *neighbor)
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
bool verify(const T &r, const Communicator &comm=Communicator_World)
const Parallel::Communicator & comm() const
void set_p_refinement_flag(const RefinementState pflag)
Definition: elem.h:2244
Elem * topological_neighbor(Elem *elem, const PointLocatorBase *point_locator, const unsigned int side)
UniquePtr< PointLocatorBase > sub_point_locator() const
Definition: mesh_base.C:531
const RemoteElem * remote_elem
Definition: remote_elem.C:57
unsigned int & libMesh::MeshRefinement::max_h_level ( )
inline

The max_h_level is the greatest refinement level an element should reach.

max_h_level is unlimited (libMesh::invalid_uint) by default

Definition at line 873 of file mesh_refinement.h.

References _max_h_level, and _use_member_parameters.

Referenced by get_mesh().

874 {
875  _use_member_parameters = true;
876  return _max_h_level;
877 }
processor_id_type libMesh::ParallelObject::n_processors ( ) const
inlineinherited
Returns
the number of processors in the group.

Definition at line 93 of file parallel_object.h.

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

Referenced by libMesh::ParmetisPartitioner::_do_repartition(), libMesh::BoundaryInfo::_find_id_maps(), libMesh::DistributedMesh::add_elem(), libMesh::DistributedMesh::add_node(), libMesh::LaplaceMeshSmoother::allgather_graph(), libMesh::FEMSystem::assembly(), libMesh::ParmetisPartitioner::assign_partitioning(), libMesh::AztecLinearSolver< T >::AztecLinearSolver(), libMesh::MeshCommunication::broadcast(), libMesh::BoundaryInfo::build_node_list_from_side_list(), libMesh::DistributedMesh::clear(), libMesh::Nemesis_IO_Helper::compute_border_node_ids(), libMesh::Nemesis_IO_Helper::construct_nemesis_filename(), libMesh::MeshTools::correct_node_proc_ids(), libMesh::UnstructuredMesh::create_pid_mesh(), libMesh::DofMap::distribute_dofs(), libMesh::DofMap::distribute_local_dofs_node_major(), libMesh::DofMap::distribute_local_dofs_var_major(), libMesh::DistributedMesh::DistributedMesh(), libMesh::EnsightIO::EnsightIO(), libMesh::MeshCommunication::gather(), libMesh::MeshCommunication::gather_neighboring_elements(), libMesh::MeshBase::get_info(), libMesh::EquationSystems::get_solution(), libMesh::DistributedVector< T >::init(), libMesh::SystemSubsetBySubdomain::init(), libMesh::ParmetisPartitioner::initialize(), libMesh::Nemesis_IO_Helper::initialize(), libMesh::DistributedMesh::insert_elem(), libMesh::MeshTools::libmesh_assert_parallel_consistent_procids< Elem >(), libMesh::MeshTools::libmesh_assert_parallel_consistent_procids< Node >(), libMesh::MeshTools::libmesh_assert_topology_consistent_procids< Node >(), libMesh::MeshTools::libmesh_assert_valid_boundary_ids(), libMesh::MeshTools::libmesh_assert_valid_dof_ids(), libMesh::MeshTools::libmesh_assert_valid_neighbors(), libMesh::MeshTools::libmesh_assert_valid_refinement_flags(), libMesh::DofMap::local_variable_indices(), libMesh::MeshBase::n_active_elem_on_proc(), libMesh::MeshBase::n_elem_on_proc(), libMesh::MeshBase::n_nodes_on_proc(), libMesh::SparsityPattern::Build::parallel_sync(), 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::SparseMatrix< T >::print(), libMesh::MeshTools::processor_bounding_box(), libMesh::NameBasedIO::read(), libMesh::Nemesis_IO::read(), libMesh::XdrIO::read(), libMesh::MeshCommunication::redistribute(), libMesh::DistributedMesh::renumber_dof_objects(), libMesh::Partitioner::repartition(), libMesh::MeshCommunication::send_coarse_ghosts(), libMesh::Partitioner::set_node_processor_ids(), libMesh::DofMap::set_nonlocal_dof_objects(), libMesh::Parallel::Sort< KeyType, IdxType >::sort(), libMesh::DistributedMesh::update_parallel_id_counts(), libMesh::GMVIO::write_binary(), libMesh::GMVIO::write_discontinuous_gmv(), libMesh::XdrIO::write_serialized_bcs_helper(), libMesh::XdrIO::write_serialized_connectivity(), libMesh::XdrIO::write_serialized_nodes(), and libMesh::XdrIO::write_serialized_nodesets().

94  { return cast_int<processor_id_type>(_communicator.size()); }
unsigned int size() const
Definition: parallel.h:679
const Parallel::Communicator & _communicator
dof_id_type & libMesh::MeshRefinement::nelem_target ( )
inline

If nelem_target is set to a nonzero value, methods like flag_elements_by_nelem_target() will attempt to keep the number of active elements in the mesh close to nelem_target.

nelem_target is 0 by default.

Definition at line 885 of file mesh_refinement.h.

References _nelem_target, and _use_member_parameters.

Referenced by get_mesh().

886 {
887  _use_member_parameters = true;
888  return _nelem_target;
889 }
unsigned char & libMesh::MeshRefinement::node_level_mismatch_limit ( )
inline

If node_level_mismatch_limit is set to a nonzero value, then refinement and coarsening will produce meshes in which the refinement level of two nodal neighbors will not differ by more than that limit. If node_level_mismatch_limit is 0, then level differences will be unlimited.

node_level_mismatch_limit is 0 by default.

Definition at line 907 of file mesh_refinement.h.

References _node_level_mismatch_limit.

Referenced by get_mesh().

908 {
910 }
unsigned char _node_level_mismatch_limit
MeshRefinement& libMesh::MeshRefinement::operator= ( const MeshRefinement )
private
signed char & libMesh::MeshRefinement::overrefined_boundary_limit ( )
inline

If overrefined_boundary_limit is set to a nonnegative value, then refinement and coarsening will produce meshes in which the refinement level of a boundary element is no more than that many levels greater than the level of any of its interior neighbors.

This may be counter-intuitive in the 1D-embedded-in-3D case: an edge has more interior neighbors than a face containing that edge.

If overrefined_boundary_limit is negative, then level differences will be unlimited.

overrefined_boundary_limit is 0 by default. This implies that adaptive coarsening can only be done on an interior element if any boundary elements on its sides are simultaneously coarsened.

Definition at line 912 of file mesh_refinement.h.

References _overrefined_boundary_limit.

Referenced by get_mesh(), and libMesh::EquationSystems::reinit().

913 {
915 }
signed char _overrefined_boundary_limit
processor_id_type libMesh::ParallelObject::processor_id ( ) const
inlineinherited
Returns
the rank of this processor in the group.

Definition at line 99 of file parallel_object.h.

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

Referenced by libMesh::BoundaryInfo::_find_id_maps(), libMesh::EquationSystems::_read_impl(), libMesh::DistributedMesh::add_elem(), libMesh::BoundaryInfo::add_elements(), libMesh::DofMap::add_neighbors_to_send_list(), libMesh::DistributedMesh::add_node(), add_node(), libMesh::MeshTools::Modification::all_tri(), libMesh::FEMSystem::assembly(), libMesh::ParmetisPartitioner::assign_partitioning(), libMesh::MeshCommunication::broadcast(), 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::BoundaryInfo::build_node_list_from_side_list(), libMesh::DofMap::build_sparsity(), libMesh::DistributedMesh::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::MeshTools::correct_node_proc_ids(), libMesh::ExodusII_IO_Helper::create(), libMesh::DistributedMesh::delete_elem(), libMesh::DistributedMesh::delete_node(), libMesh::MeshCommunication::delete_remote_elements(), libMesh::DofMap::distribute_dofs(), libMesh::DofMap::distribute_local_dofs_node_major(), libMesh::DofMap::distribute_local_dofs_var_major(), libMesh::DistributedMesh::DistributedMesh(), libMesh::EnsightIO::EnsightIO(), libMesh::MeshFunction::find_element(), libMesh::MeshFunction::find_elements(), libMesh::UnstructuredMesh::find_neighbors(), libMesh::MeshCommunication::gather(), libMesh::MeshCommunication::gather_neighboring_elements(), 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::DofMap::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::EquationSystems::get_solution(), libMesh::Nemesis_IO_Helper::get_ss_param_global(), libMesh::SparsityPattern::Build::handle_vi_vj(), libMesh::DistributedVector< T >::init(), libMesh::SystemSubsetBySubdomain::init(), libMesh::ParmetisPartitioner::initialize(), libMesh::ExodusII_IO_Helper::initialize(), libMesh::ExodusII_IO_Helper::initialize_element_variables(), libMesh::ExodusII_IO_Helper::initialize_global_variables(), libMesh::ExodusII_IO_Helper::initialize_nodal_variables(), libMesh::DistributedMesh::insert_elem(), libMesh::DofMap::is_evaluable(), libMesh::SparsityPattern::Build::join(), libMesh::MeshTools::libmesh_assert_parallel_consistent_procids< Elem >(), libMesh::MeshTools::libmesh_assert_parallel_consistent_procids< Node >(), libMesh::MeshTools::libmesh_assert_valid_neighbors(), libMesh::DistributedMesh::libmesh_assert_valid_parallel_object_ids(), libMesh::DofMap::local_variable_indices(), make_coarsening_compatible(), libMesh::MeshBase::n_active_local_elem(), libMesh::BoundaryInfo::n_boundary_conds(), libMesh::BoundaryInfo::n_edge_conds(), libMesh::System::n_local_dofs(), libMesh::MeshBase::n_local_elem(), libMesh::MeshBase::n_local_nodes(), libMesh::BoundaryInfo::n_nodeset_conds(), libMesh::BoundaryInfo::n_shellface_conds(), libMesh::WeightedPatchRecoveryErrorEstimator::EstimateError::operator()(), libMesh::SparsityPattern::Build::operator()(), libMesh::PatchRecoveryErrorEstimator::EstimateError::operator()(), libMesh::SparsityPattern::Build::parallel_sync(), libMesh::MetisPartitioner::partition_range(), libMesh::System::point_gradient(), libMesh::System::point_hessian(), libMesh::System::point_value(), libMesh::SparseMatrix< T >::print(), libMesh::NumericVector< T >::print_global(), 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::NameBasedIO::read(), libMesh::Nemesis_IO::read(), libMesh::XdrIO::read(), libMesh::ExodusII_IO_Helper::read_elem_num_map(), libMesh::ExodusII_IO_Helper::read_node_num_map(), libMesh::XdrIO::read_serialized_bc_names(), libMesh::XdrIO::read_serialized_bcs_helper(), libMesh::XdrIO::read_serialized_connectivity(), libMesh::XdrIO::read_serialized_nodes(), libMesh::XdrIO::read_serialized_nodesets(), libMesh::XdrIO::read_serialized_subdomain_names(), libMesh::MeshCommunication::redistribute(), libMesh::DistributedMesh::renumber_dof_objects(), libMesh::MeshCommunication::send_coarse_ghosts(), libMesh::Partitioner::set_node_processor_ids(), libMesh::DofMap::set_nonlocal_dof_objects(), libMesh::LaplaceMeshSmoother::smooth(), libMesh::MeshTools::total_weight(), libMesh::Parallel::Packing< Node * >::unpack(), libMesh::Parallel::Packing< Elem * >::unpack(), libMesh::DistributedMesh::update_parallel_id_counts(), libMesh::MeshTools::weight(), libMesh::NameBasedIO::write(), libMesh::XdrIO::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::write_global_data(), libMesh::ExodusII_IO_Helper::write_global_values(), libMesh::ExodusII_IO::write_information_records(), libMesh::ExodusII_IO_Helper::write_information_records(), libMesh::ExodusII_IO_Helper::write_nodal_coordinates(), 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::Nemesis_IO_Helper::write_nodesets(), libMesh::ExodusII_IO_Helper::write_nodesets(), libMesh::XdrIO::write_serialized_bc_names(), libMesh::XdrIO::write_serialized_bcs_helper(), libMesh::XdrIO::write_serialized_connectivity(), libMesh::XdrIO::write_serialized_nodes(), libMesh::XdrIO::write_serialized_nodesets(), libMesh::XdrIO::write_serialized_subdomain_names(), libMesh::Nemesis_IO_Helper::write_sidesets(), libMesh::ExodusII_IO_Helper::write_sidesets(), libMesh::ExodusII_IO::write_timestep(), and libMesh::ExodusII_IO_Helper::write_timestep().

100  { return cast_int<processor_id_type>(_communicator.rank()); }
const Parallel::Communicator & _communicator
unsigned int rank() const
Definition: parallel.h:677
bool libMesh::MeshRefinement::refine_and_coarsen_elements ( )

Refines and coarsens user-requested elements. Will also refine/coarsen additional elements to satisfy level-one rule. It is possible that for a given set of refinement flags there is actually no change upon calling this member function. Consequently, this function returns true if the mesh actually changed (hence data needs to be projected) and false otherwise.

This function used to take an argument, maintain_level_one - new code should use face_level_mismatch_limit() instead.

Definition at line 478 of file mesh_refinement.C.

References _coarsen_elements(), _face_level_mismatch_limit, _mesh, _refine_elements(), _smooth_flags(), libMesh::Elem::active(), libMesh::Elem::DO_NOTHING, libMesh::MeshBase::elements_begin(), libMesh::MeshBase::elements_end(), libMesh::Elem::INACTIVE, libMesh::Elem::JUST_REFINED, libMesh::libmesh_assert(), libMesh::MeshBase::libmesh_assert_valid_parallel_ids(), make_coarsening_compatible(), make_flags_parallel_consistent(), make_refinement_compatible(), libMesh::out, libMesh::MeshBase::prepare_for_use(), libMesh::Elem::refinement_flag(), libMesh::Elem::set_p_refinement_flag(), libMesh::Elem::set_refinement_flag(), test_level_one(), and test_unflagged().

Referenced by libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

479 {
480  // This function must be run on all processors at once
481  parallel_object_only();
482 
483  // We can't yet turn a non-level-one mesh into a level-one mesh
486 
487  // Possibly clean up the refinement flags from
488  // a previous step
489  MeshBase::element_iterator elem_it = _mesh.elements_begin();
490  const MeshBase::element_iterator elem_end = _mesh.elements_end();
491 
492  for ( ; elem_it != elem_end; ++elem_it)
493  {
494  // Pointer to the element
495  Elem * elem = *elem_it;
496 
497  // Set refinement flag to INACTIVE if the
498  // element isn't active
499  if ( !elem->active())
500  {
501  elem->set_refinement_flag(Elem::INACTIVE);
502  elem->set_p_refinement_flag(Elem::INACTIVE);
503  }
504 
505  // This might be left over from the last step
506  if (elem->refinement_flag() == Elem::JUST_REFINED)
507  elem->set_refinement_flag(Elem::DO_NOTHING);
508  }
509 
510  // Parallel consistency has to come first, or coarsening
511  // along processor boundaries might occasionally be falsely
512  // prevented
513  bool flags_were_consistent = this->make_flags_parallel_consistent();
514 
515  // In theory, we should be able to remove the above call, which can
516  // be expensive and should be unnecessary. In practice, doing
517  // consistent flagging in parallel is hard, it's impossible to
518  // verify at the library level if it's being done by user code, and
519  // we don't want to abort large parallel runs in opt mode... but we
520  // do want to warn that they should be fixed.
521  if (!flags_were_consistent)
522  {
523  libMesh::out << "Refinement flags were not consistent between processors!\n"
524  << "Correcting and continuing.";
525  }
526 
527  // Smooth refinement and coarsening flags
528  _smooth_flags(true, true);
529 
530  // First coarsen the flagged elements.
531  const bool coarsening_changed_mesh =
532  this->_coarsen_elements ();
533 
534  // First coarsen the flagged elements.
535  // FIXME: test_level_one now tests consistency across periodic
536  // boundaries, which requires a point_locator, which just got
537  // invalidated by _coarsen_elements() and hasn't yet been cleared by
538  // prepare_for_use().
539 
540  // libmesh_assert(this->make_coarsening_compatible());
541  // libmesh_assert(this->make_refinement_compatible());
542 
543  // FIXME: This won't pass unless we add a redundant find_neighbors()
544  // call or replace find_neighbors() with on-the-fly neighbor updating
545  // libmesh_assert(!this->eliminate_unrefined_patches());
546 
547  // We can't contract the mesh ourselves anymore - a System might
548  // need to restrict old coefficient vectors first
549  // _mesh.contract();
550 
551  // First coarsen the flagged elements.
552  // Now refine the flagged elements. This will
553  // take up some space, maybe more than what was freed.
554  const bool refining_changed_mesh =
555  this->_refine_elements();
556 
557  // First coarsen the flagged elements.
558  // Finally, the new mesh needs to be prepared for use
559  if (coarsening_changed_mesh || refining_changed_mesh)
560  {
561 #ifdef DEBUG
563 #endif
564 
565  _mesh.prepare_for_use (/*skip_renumber =*/false);
566 
572  // FIXME: This won't pass unless we add a redundant find_neighbors()
573  // call or replace find_neighbors() with on-the-fly neighbor updating
574  // libmesh_assert(!this->eliminate_unrefined_patches());
575 
576  return true;
577  }
578  else
579  {
585  }
586 
587  // Otherwise there was no change in the mesh,
588  // let the user know. Also, there is no need
589  // to prepare the mesh for use since it did not change.
590  return false;
591 
592 }
virtual void libmesh_assert_valid_parallel_ids() const
Definition: mesh_base.h:916
libmesh_assert(j)
virtual element_iterator elements_begin()=0
bool test_level_one(bool libmesh_assert_yes=false)
unsigned char _face_level_mismatch_limit
virtual element_iterator elements_end()=0
void prepare_for_use(const bool skip_renumber_nodes_and_elements=false, const bool skip_find_neighbors=false)
Definition: mesh_base.C:174
bool test_unflagged(bool libmesh_assert_yes=false)
void _smooth_flags(bool refining, bool coarsening)
OStreamProxy out(std::cout)
bool libMesh::MeshRefinement::refine_elements ( )

Only refines the user-requested elements. It is possible that for a given set of refinement flags there is actually no change upon calling this member function. Consequently, this function returns true if the mesh actually changed (hence data needs to be projected) and false otherwise.

This function used to take an argument, maintain_level_one - new code should use face_level_mismatch_limit() instead.

Definition at line 681 of file mesh_refinement.C.

References _face_level_mismatch_limit, _mesh, _refine_elements(), _smooth_flags(), libMesh::Elem::active(), libMesh::Elem::DO_NOTHING, libMesh::MeshBase::elements_begin(), libMesh::MeshBase::elements_end(), get_flag, libMesh::Elem::INACTIVE, libMesh::Elem::JUST_REFINED, libMesh::libmesh_assert(), make_flags_parallel_consistent(), make_refinement_compatible(), mesh, libMesh::out, parallel_consistent, libMesh::MeshBase::prepare_for_use(), libMesh::Elem::refinement_flag(), set_flag, libMesh::Elem::set_p_refinement_flag(), libMesh::Elem::set_refinement_flag(), and test_level_one().

Referenced by libMesh::EquationSystems::reinit(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

682 {
683  // This function must be run on all processors at once
684  parallel_object_only();
685 
688 
689  // Possibly clean up the refinement flags from
690  // a previous step
691  MeshBase::element_iterator elem_it = _mesh.elements_begin();
692  const MeshBase::element_iterator elem_end = _mesh.elements_end();
693 
694  for ( ; elem_it != elem_end; ++elem_it)
695  {
696  // Pointer to the element
697  Elem * elem = *elem_it;
698 
699  // Set refinement flag to INACTIVE if the
700  // element isn't active
701  if ( !elem->active())
702  {
703  elem->set_refinement_flag(Elem::INACTIVE);
704  elem->set_p_refinement_flag(Elem::INACTIVE);
705  }
706 
707  // This might be left over from the last step
708  if (elem->refinement_flag() == Elem::JUST_REFINED)
709  elem->set_refinement_flag(Elem::DO_NOTHING);
710  }
711 
712 
713 
714  // Parallel consistency has to come first, or coarsening
715  // along processor boundaries might occasionally be falsely
716  // prevented
717  bool flags_were_consistent = this->make_flags_parallel_consistent();
718 
719  // In theory, we should be able to remove the above call, which can
720  // be expensive and should be unnecessary. In practice, doing
721  // consistent flagging in parallel is hard, it's impossible to
722  // verify at the library level if it's being done by user code, and
723  // we don't want to abort large parallel runs in opt mode... but we
724  // do want to warn that they should be fixed.
725  libmesh_assert(flags_were_consistent);
726  if (!flags_were_consistent)
727  {
728  libMesh::out << "Refinement flags were not consistent between processors!\n"
729  << "Correcting and continuing.";
730  }
731 
732  // Smooth refinement flags
733  _smooth_flags(true, false);
734 
735  // Now refine the flagged elements. This will
736  // take up some space, maybe more than what was freed.
737  const bool mesh_changed =
738  this->_refine_elements();
739 
743  // FIXME: This won't pass unless we add a redundant find_neighbors()
744  // call or replace find_neighbors() with on-the-fly neighbor updating
745  // libmesh_assert(!this->eliminate_unrefined_patches());
746 
747  // Finally, the new mesh needs to be prepared for use
748  if (mesh_changed)
749  _mesh.prepare_for_use (/*skip_renumber =*/false);
750 
751  return mesh_changed;
752 }
libmesh_assert(j)
virtual element_iterator elements_begin()=0
bool test_level_one(bool libmesh_assert_yes=false)
unsigned char _face_level_mismatch_limit
virtual element_iterator elements_end()=0
void prepare_for_use(const bool skip_renumber_nodes_and_elements=false, const bool skip_find_neighbors=false)
Definition: mesh_base.C:174
void _smooth_flags(bool refining, bool coarsening)
OStreamProxy out(std::cout)
Real & libMesh::MeshRefinement::refine_fraction ( )
inline

The refine_fraction sets either a desired target or a desired maximum number of elements to flag for refinement, depending on which flag_elements_by method is called.

refine_fraction must be in $ [0,1] $, and is 0.3 by default.

Definition at line 861 of file mesh_refinement.h.

References _refine_fraction, and _use_member_parameters.

Referenced by get_mesh(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

862 {
863  _use_member_parameters = true;
864  return _refine_fraction;
865 }
void libMesh::MeshRefinement::set_enforce_mismatch_limit_prior_to_refinement ( bool  enforce)
inline

Set _enforce_mismatch_limit_prior_to_refinement option. Defaults to false. Deprecated - use enforce_mismatch_limit_prior_to_refinement() instead.

Definition at line 928 of file mesh_refinement.h.

References enforce_mismatch_limit_prior_to_refinement().

Referenced by get_mesh().

929 {
930  libmesh_deprecated();
932 }
bool & enforce_mismatch_limit_prior_to_refinement()
void libMesh::MeshRefinement::set_periodic_boundaries_ptr ( PeriodicBoundaries pb_ptr)
void libMesh::MeshRefinement::switch_h_to_p_refinement ( )

Takes a mesh whose elements are flagged for h refinement and coarsening, and switches those flags to request p refinement and coarsening instead.

Definition at line 663 of file mesh_refinement_flagging.C.

References _mesh, libMesh::Elem::DO_NOTHING, libMesh::MeshBase::elements_begin(), libMesh::MeshBase::elements_end(), and libMesh::Elem::INACTIVE.

Referenced by libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

664 {
665  MeshBase::element_iterator elem_it = _mesh.elements_begin();
666  const MeshBase::element_iterator elem_end = _mesh.elements_end();
667 
668  for ( ; elem_it != elem_end; ++elem_it)
669  {
670  if ((*elem_it)->active())
671  {
672  (*elem_it)->set_p_refinement_flag((*elem_it)->refinement_flag());
673  (*elem_it)->set_refinement_flag(Elem::DO_NOTHING);
674  }
675  else
676  {
677  (*elem_it)->set_p_refinement_flag((*elem_it)->refinement_flag());
678  (*elem_it)->set_refinement_flag(Elem::INACTIVE);
679  }
680  }
681 }
virtual element_iterator elements_begin()=0
virtual element_iterator elements_end()=0
bool libMesh::MeshRefinement::test_level_one ( bool  libmesh_assert_yes = false)

Returns true if and only if the mesh is level one smooth Returns false otherwise Aborts the program if libmesh_assert_yes is true and the mesh is not level one smooth

Definition at line 339 of file mesh_refinement.C.

References _mesh, _periodic_boundaries, libMesh::Elem::active(), libMesh::MeshBase::active_local_elements_begin(), libMesh::MeshBase::active_local_elements_end(), libMesh::ParallelObject::comm(), libMesh::Elem::level(), libMesh::libmesh_assert(), libmesh_nullptr, libMesh::Parallel::Communicator::max(), libMesh::Elem::n_neighbors(), libMesh::out, libMesh::Elem::p_level(), libMesh::remote_elem, libMesh::MeshBase::sub_point_locator(), topological_neighbor(), and libMesh::Parallel::verify().

Referenced by coarsen_elements(), refine_and_coarsen_elements(), refine_elements(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

340 {
341  // This function must be run on all processors at once
342  parallel_object_only();
343 
344  // We may need a PointLocator for topological_neighbor() tests
345  // later, which we need to make sure gets constructed on all
346  // processors at once.
347  UniquePtr<PointLocatorBase> point_locator;
348 
349 #ifdef LIBMESH_ENABLE_PERIODIC
350  bool has_periodic_boundaries =
352  libmesh_assert(this->comm().verify(has_periodic_boundaries));
353 
354  if (has_periodic_boundaries)
355  point_locator = _mesh.sub_point_locator();
356 #endif
357 
358  MeshBase::element_iterator elem_it = _mesh.active_local_elements_begin();
359  const MeshBase::element_iterator elem_end = _mesh.active_local_elements_end();
360 
361  bool failure = false;
362 
363 #ifndef NDEBUG
364  Elem * failed_elem = libmesh_nullptr;
365  Elem * failed_neighbor = libmesh_nullptr;
366 #endif // !NDEBUG
367 
368  for ( ; elem_it != elem_end && !failure; ++elem_it)
369  {
370  // Pointer to the element
371  Elem * elem = *elem_it;
372 
373  for (unsigned int n=0; n<elem->n_neighbors(); n++)
374  {
375  Elem * neighbor =
376  topological_neighbor(elem, point_locator.get(), n);
377 
378  if (!neighbor || !neighbor->active() ||
379  neighbor == remote_elem)
380  continue;
381 
382  if ((neighbor->level() + 1 < elem->level()) ||
383  (neighbor->p_level() + 1 < elem->p_level()) ||
384  (neighbor->p_level() > elem->p_level() + 1))
385  {
386  failure = true;
387 #ifndef NDEBUG
388  failed_elem = elem;
389  failed_neighbor = neighbor;
390 #endif // !NDEBUG
391  break;
392  }
393  }
394  }
395 
396  // If any processor failed, we failed globally
397  this->comm().max(failure);
398 
399  if (failure)
400  {
401  // We didn't pass the level one test, so libmesh_assert that
402  // we're allowed not to
403 #ifndef NDEBUG
404  if (libmesh_assert_pass)
405  {
406  libMesh::out << "MeshRefinement Level one failure, element: "
407  << *failed_elem
408  << std::endl;
409  libMesh::out << "MeshRefinement Level one failure, neighbor: "
410  << *failed_neighbor
411  << std::endl;
412  }
413 #endif // !NDEBUG
414  libmesh_assert(!libmesh_assert_pass);
415  return false;
416  }
417  return true;
418 }
const class libmesh_nullptr_t libmesh_nullptr
PeriodicBoundaries * _periodic_boundaries
libmesh_assert(j)
virtual element_iterator active_local_elements_begin()=0
bool verify(const T &r, const Communicator &comm=Communicator_World)
const Parallel::Communicator & comm() const
OStreamProxy out(std::cout)
Elem * topological_neighbor(Elem *elem, const PointLocatorBase *point_locator, const unsigned int side)
virtual element_iterator active_local_elements_end()=0
UniquePtr< PointLocatorBase > sub_point_locator() const
Definition: mesh_base.C:531
const RemoteElem * remote_elem
Definition: remote_elem.C:57
bool libMesh::MeshRefinement::test_unflagged ( bool  libmesh_assert_yes = false)

Returns true if and only if the mesh has no elements flagged to be coarsened or refined Returns false otherwise Aborts the program if libmesh_assert_yes is true and the mesh has flagged elements

Definition at line 422 of file mesh_refinement.C.

References _mesh, libMesh::MeshBase::active_local_elements_begin(), libMesh::MeshBase::active_local_elements_end(), libMesh::Elem::COARSEN, libMesh::ParallelObject::comm(), libMesh::libmesh_assert(), libmesh_nullptr, libMesh::Parallel::Communicator::max(), libMesh::out, libMesh::Elem::p_refinement_flag(), libMesh::Elem::REFINE, and libMesh::Elem::refinement_flag().

Referenced by refine_and_coarsen_elements(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

423 {
424  // This function must be run on all processors at once
425  parallel_object_only();
426 
427  bool found_flag = false;
428 
429  // Search for local flags
430  MeshBase::element_iterator elem_it = _mesh.active_local_elements_begin();
431  const MeshBase::element_iterator elem_end = _mesh.active_local_elements_end();
432 
433 #ifndef NDEBUG
434  Elem * failed_elem = libmesh_nullptr;
435 #endif
436 
437  for ( ; elem_it != elem_end; ++elem_it)
438  {
439  // Pointer to the element
440  Elem * elem = *elem_it;
441 
442  if (elem->refinement_flag() == Elem::REFINE ||
443  elem->refinement_flag() == Elem::COARSEN ||
444  elem->p_refinement_flag() == Elem::REFINE ||
445  elem->p_refinement_flag() == Elem::COARSEN)
446  {
447  found_flag = true;
448 #ifndef NDEBUG
449  failed_elem = elem;
450 #endif
451  break;
452  }
453  }
454 
455  // If we found a flag on any processor, it counts
456  this->comm().max(found_flag);
457 
458  if (found_flag)
459  {
460 #ifndef NDEBUG
461  if (libmesh_assert_pass)
462  {
463  libMesh::out <<
464  "MeshRefinement test_unflagged failure, element: " <<
465  *failed_elem << std::endl;
466  }
467 #endif
468  // We didn't pass the "elements are unflagged" test,
469  // so libmesh_assert that we're allowed not to
470  libmesh_assert(!libmesh_assert_pass);
471  return false;
472  }
473  return true;
474 }
const class libmesh_nullptr_t libmesh_nullptr
libmesh_assert(j)
virtual element_iterator active_local_elements_begin()=0
const Parallel::Communicator & comm() const
OStreamProxy out(std::cout)
virtual element_iterator active_local_elements_end()=0
Elem * libMesh::MeshRefinement::topological_neighbor ( Elem elem,
const PointLocatorBase point_locator,
const unsigned int  side 
)
private

Local dispatch function for getting the correct topological neighbor from the Elem class

Definition at line 1813 of file mesh_refinement.C.

References _mesh, _periodic_boundaries, libMesh::libmesh_assert(), libMesh::Elem::neighbor_ptr(), and libMesh::Elem::topological_neighbor().

Referenced by get_mesh(), make_coarsening_compatible(), make_refinement_compatible(), and test_level_one().

1816 {
1817 #ifdef LIBMESH_ENABLE_PERIODIC
1818  if (_periodic_boundaries && !_periodic_boundaries->empty())
1819  {
1820  libmesh_assert(point_locator);
1821  return elem->topological_neighbor(side, _mesh, *point_locator, _periodic_boundaries);
1822  }
1823 #endif
1824  return elem->neighbor_ptr(side);
1825 }
unsigned short int side
Definition: xdr_io.C:49
PeriodicBoundaries * _periodic_boundaries
libmesh_assert(j)
signed char & libMesh::MeshRefinement::underrefined_boundary_limit ( )
inline

If underrefined_boundary_limit is set to a nonnegative value, then refinement and coarsening will produce meshes in which the refinement level of an element is no more than that many levels greater than the level of any boundary elements on its sides.

If underrefined_boundary_limit is negative, then level differences will be unlimited.

underrefined_boundary_limit is 0 by default. This implies that adaptive coarsening can only be done on a boundary element if any interior elements it is on the side of are simultaneously coarsened.

Definition at line 917 of file mesh_refinement.h.

References _underrefined_boundary_limit.

Referenced by get_mesh(), and libMesh::EquationSystems::reinit().

918 {
920 }
signed char _underrefined_boundary_limit
void libMesh::MeshRefinement::uniformly_coarsen ( unsigned int  n = 1)

Attempts to uniformly coarsen the mesh n times.

Definition at line 1782 of file mesh_refinement.C.

References _coarsen_elements(), _mesh, libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), clean_refinement_flags(), libMesh::Elem::COARSEN, libMesh::Elem::COARSEN_INACTIVE, and libMesh::MeshBase::prepare_for_use().

Referenced by libMesh::UniformRefinementEstimator::_estimate_error(), libMesh::AdjointRefinementEstimator::estimate_error(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

1783 {
1784  // Coarsen n times
1785  for (unsigned int rstep=0; rstep<n; rstep++)
1786  {
1787  // Clean up the refinement flags
1788  this->clean_refinement_flags();
1789 
1790  // Flag all the active elements for coarsening
1791  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
1792  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
1793 
1794  for ( ; elem_it != elem_end; ++elem_it)
1795  {
1796  (*elem_it)->set_refinement_flag(Elem::COARSEN);
1797  if ((*elem_it)->parent())
1798  (*elem_it)->parent()->set_refinement_flag(Elem::COARSEN_INACTIVE);
1799  }
1800 
1801  // Coarsen all the elements we just flagged.
1802  this->_coarsen_elements();
1803  }
1804 
1805 
1806  // Finally, the new mesh probably needs to be prepared for use
1807  if (n > 0)
1808  _mesh.prepare_for_use (/*skip_renumber =*/false);
1809 }
void prepare_for_use(const bool skip_renumber_nodes_and_elements=false, const bool skip_find_neighbors=false)
Definition: mesh_base.C:174
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
void libMesh::MeshRefinement::uniformly_p_coarsen ( unsigned int  n = 1)

Attempts to uniformly p coarsen the mesh n times.

Definition at line 1732 of file mesh_refinement.C.

References _mesh, libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), and libMesh::Elem::JUST_COARSENED.

Referenced by libMesh::UniformRefinementEstimator::_estimate_error(), libMesh::AdjointRefinementEstimator::estimate_error(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

1733 {
1734  // Coarsen p times
1735  for (unsigned int rstep=0; rstep<n; rstep++)
1736  {
1737  // P coarsen all the active elements
1738  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
1739  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
1740 
1741  for ( ; elem_it != elem_end; ++elem_it)
1742  {
1743  if ((*elem_it)->p_level() > 0)
1744  {
1745  (*elem_it)->set_p_level((*elem_it)->p_level()-1);
1746  (*elem_it)->set_p_refinement_flag(Elem::JUST_COARSENED);
1747  }
1748  }
1749  }
1750 }
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
void libMesh::MeshRefinement::uniformly_p_refine ( unsigned int  n = 1)

Uniformly p refines the mesh n times.

Definition at line 1713 of file mesh_refinement.C.

References _mesh, libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), and libMesh::Elem::JUST_REFINED.

Referenced by libMesh::UniformRefinementEstimator::_estimate_error(), libMesh::AdjointRefinementEstimator::estimate_error(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

1714 {
1715  // Refine n times
1716  for (unsigned int rstep=0; rstep<n; rstep++)
1717  {
1718  // P refine all the active elements
1719  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
1720  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
1721 
1722  for ( ; elem_it != elem_end; ++elem_it)
1723  {
1724  (*elem_it)->set_p_level((*elem_it)->p_level()+1);
1725  (*elem_it)->set_p_refinement_flag(Elem::JUST_REFINED);
1726  }
1727  }
1728 }
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
void libMesh::MeshRefinement::uniformly_refine ( unsigned int  n = 1)

Uniformly refines the mesh n times.

Definition at line 1754 of file mesh_refinement.C.

References _mesh, _refine_elements(), libMesh::MeshBase::active_elements_begin(), libMesh::MeshBase::active_elements_end(), clean_refinement_flags(), libMesh::MeshBase::prepare_for_use(), and libMesh::Elem::REFINE.

Referenced by libMesh::UniformRefinementEstimator::_estimate_error(), libMesh::AdjointRefinementEstimator::estimate_error(), and libMesh::MeshRefinement::ElementFlagging::~ElementFlagging().

1755 {
1756  // Refine n times
1757  // FIXME - this won't work if n>1 and the mesh
1758  // has already been attached to an equation system
1759  for (unsigned int rstep=0; rstep<n; rstep++)
1760  {
1761  // Clean up the refinement flags
1762  this->clean_refinement_flags();
1763 
1764  // Flag all the active elements for refinement.
1765  MeshBase::element_iterator elem_it = _mesh.active_elements_begin();
1766  const MeshBase::element_iterator elem_end = _mesh.active_elements_end();
1767 
1768  for ( ; elem_it != elem_end; ++elem_it)
1769  (*elem_it)->set_refinement_flag(Elem::REFINE);
1770 
1771  // Refine all the elements we just flagged.
1772  this->_refine_elements();
1773  }
1774 
1775  // Finally, the new mesh probably needs to be prepared for use
1776  if (n > 0)
1777  _mesh.prepare_for_use (/*skip_renumber =*/false);
1778 }
void prepare_for_use(const bool skip_renumber_nodes_and_elements=false, const bool skip_find_neighbors=false)
Definition: mesh_base.C:174
virtual element_iterator active_elements_begin()=0
virtual element_iterator active_elements_end()=0
void libMesh::MeshRefinement::update_nodes_map ( )
private

Updates the _new_nodes_map

Definition at line 332 of file mesh_refinement.C.

References _mesh, _new_nodes_map, and libMesh::TopologyMap::init().

Referenced by _coarsen_elements(), _refine_elements(), and get_mesh().

333 {
334  this->_new_nodes_map.init(_mesh);
335 }
void init(MeshBase &)
Definition: topology_map.C:34

Member Data Documentation

Real libMesh::MeshRefinement::_absolute_global_tolerance
private
bool libMesh::MeshRefinement::_coarsen_by_parents
private
Real libMesh::MeshRefinement::_coarsen_threshold
private
unsigned char libMesh::MeshRefinement::_edge_level_mismatch_limit
private

Definition at line 756 of file mesh_refinement.h.

Referenced by _smooth_flags(), and edge_level_mismatch_limit().

bool libMesh::MeshRefinement::_enforce_mismatch_limit_prior_to_refinement
private

This option enforces the mismatch level prior to refinement by checking if refining any element marked for refinement would cause a mismatch greater than the limit. Applies to all mismatch methods.

Calling this with node_level_mismatch_limit() = 1 would transform this mesh:

* o-------o-------o-------o-------o
* |       |       |       |       |
* |       |       |       |       |
* |       |       |       |       |
* |       |       |       |       |
* |       |       |       |       |
* o-------o---o---o-------o-------o
* |       |   :   |       |       |
* |       |   :   |       |       |
* |       o...o...o       |       |
* |       |   :   |       |       |
* |       |   :   |       |       |
* o-------o---o---o-------o-------o
* |       |       |               |
* |       |       |               |
* |       |       |               |
* |       |       |               |
* |       |       |               |
* o-------o-------o               |
* |       |       |               |
* |       |       |               |
* |       |       |               |
* |       |       |               |
* |       |       |               |
* o-------o-------o---------------o
* 

into this:

* o-------o-------o-------o-------o
* |       |       |       |       |
* |       |       |       |       |
* |       |       |       |       |
* |       |       |       |       |
* |       |       |       |       |
* o-------o-------o-------o-------o
* |       |       |       |       |
* |       |       |       |       |
* |       |       |       |       |
* |       |       |       |       |
* |       |       |       |       |
* o-------o-------o-------o-------o
* |       |       |       :       |
* |       |       |       :       |
* |       |       |       :       |
* |       |       |       :       |
* |       |       |       :       |
* o-------o-------o.......o.......o
* |       |       |       :       |
* |       |       |       :       |
* |       |       |       :       |
* |       |       |       :       |
* |       |       |       :       |
* o-------o-------o-------o-------o
* 

by moving the refinement flag to the indicated element.

Default value is false.

Definition at line 830 of file mesh_refinement.h.

Referenced by enforce_mismatch_limit_prior_to_refinement(), limit_level_mismatch_at_edge(), and limit_level_mismatch_at_node().

unsigned char libMesh::MeshRefinement::_face_level_mismatch_limit
private
dof_id_type libMesh::MeshRefinement::_nelem_target
private

Definition at line 751 of file mesh_refinement.h.

Referenced by flag_elements_by_nelem_target(), and nelem_target().

TopologyMap libMesh::MeshRefinement::_new_nodes_map
private

Data structure that holds the new nodes information.

Definition at line 723 of file mesh_refinement.h.

Referenced by add_node(), clear(), and update_nodes_map().

unsigned char libMesh::MeshRefinement::_node_level_mismatch_limit
private

Definition at line 757 of file mesh_refinement.h.

Referenced by _smooth_flags(), and node_level_mismatch_limit().

signed char libMesh::MeshRefinement::_overrefined_boundary_limit
private

Definition at line 759 of file mesh_refinement.h.

Referenced by _smooth_flags(), and overrefined_boundary_limit().

PeriodicBoundaries* libMesh::MeshRefinement::_periodic_boundaries
private
signed char libMesh::MeshRefinement::_underrefined_boundary_limit
private

Definition at line 760 of file mesh_refinement.h.

Referenced by _smooth_flags(), and underrefined_boundary_limit().

bool libMesh::MeshRefinement::_use_member_parameters
private

For backwards compatibility, we initialize this as false and then set it to true if the user uses any of the refinement parameter accessor functions

Definition at line 735 of file mesh_refinement.h.

Referenced by absolute_global_tolerance(), coarsen_by_parents(), coarsen_fraction(), coarsen_threshold(), flag_elements_by_elem_fraction(), flag_elements_by_error_fraction(), flag_elements_by_mean_stddev(), max_h_level(), nelem_target(), and refine_fraction().


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