libMesh
Public Member Functions | Public Attributes | Protected Member Functions | List of all members
libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::ProjectVertices Struct Reference

#include <generic_projector.h>

Inheritance diagram for libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::ProjectVertices:
[legend]

Public Member Functions

 ProjectVertices (GenericProjector &p)
 
 ProjectVertices (ProjectVertices &p_v, Threads::split)
 
void operator() (const node_range &range)
 
void insert_id (dof_id_type id, const FValue &val, processor_id_type pid)
 
void insert_ids (const std::vector< dof_id_type > &ids, const std::vector< FValue > &vals, processor_id_type pid)
 
void construct_projection (const std::vector< dof_id_type > &dof_indices_var, const std::vector< unsigned int > &involved_dofs, unsigned int var_component, const Node *node, const FEBase &fe)
 
void insert_id (dof_id_type id, const FValue &val, processor_id_type pid)
 
void insert_ids (const std::vector< dof_id_type > &ids, const std::vector< FValue > &vals, processor_id_type pid)
 
void find_dofs_to_send (const Node &node, const Elem &elem, unsigned short node_num, const var_set &vars)
 
void join (const SubFunctor &other)
 

Public Attributes

ProjectionAction action
 
FFunctor f
 
std::unique_ptr< GFunctor > g
 
const Systemsystem
 
FEMContext context
 
std::vector< FEContinuityconts
 
GenericProjectorprojector
 
std::unordered_map< dof_id_type, std::pair< FValue, processor_id_type > > new_ids_to_push
 
std::unordered_map< dof_id_type, FValue > new_ids_to_save
 

Protected Member Functions

void construct_projection (const std::vector< dof_id_type > &dof_indices_var, const std::vector< unsigned int > &involved_dofs, unsigned int var_component, const Node *node, const FEBase &fe)
 

Detailed Description

template<typename FFunctor, typename GFunctor, typename FValue, typename ProjectionAction>
struct libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::ProjectVertices

Definition at line 267 of file generic_projector.h.

Constructor & Destructor Documentation

◆ ProjectVertices() [1/2]

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::ProjectVertices::ProjectVertices ( GenericProjector p)
inline

Definition at line 268 of file generic_projector.h.

268 : SubProjector(p) {}

◆ ProjectVertices() [2/2]

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::ProjectVertices::ProjectVertices ( ProjectVertices p_v,
Threads::split   
)
inline

Definition at line 270 of file generic_projector.h.

270 : SubProjector(p_v.projector) {}

Member Function Documentation

◆ construct_projection() [1/2]

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
void libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubProjector::construct_projection ( const std::vector< dof_id_type > &  dof_indices_var,
const std::vector< unsigned int > &  involved_dofs,
unsigned int  var_component,
const Node node,
const FEBase fe 
)
protectedinherited

Definition at line 2501 of file generic_projector.h.

2506 {
2507  const std::vector<Real> & JxW = fe.get_JxW();
2508  const std::vector<std::vector<Real>> & phi = fe.get_phi();
2509  const std::vector<std::vector<RealGradient>> * dphi = nullptr;
2510  const std::vector<Point> & xyz_values = fe.get_xyz();
2511  const FEContinuity cont = fe.get_continuity();
2512  const std::unordered_map<dof_id_type, FValue> & ids_to_save =
2513  this->projector.ids_to_save;
2514 
2515  if (cont == C_ONE)
2516  dphi = &(fe.get_dphi());
2517 
2518  const unsigned int n_involved_dofs =
2519  cast_int<unsigned int>(involved_dofs.size());
2520 
2521  std::vector<dof_id_type> free_dof_ids;
2522  DenseVector<FValue> Uinvolved(n_involved_dofs);
2523  std::vector<char> dof_is_fixed(n_involved_dofs, false); // bools
2524 
2525  for (auto i : IntRange<unsigned int>(0, n_involved_dofs))
2526  {
2527  const dof_id_type id = dof_indices_var[involved_dofs[i]];
2528  auto iter = ids_to_save.find(id);
2529  if (iter == ids_to_save.end())
2530  free_dof_ids.push_back(id);
2531  else
2532  {
2533  dof_is_fixed[i] = true;
2534  Uinvolved(i) = iter->second;
2535  }
2536  }
2537 
2538  const unsigned int free_dofs = free_dof_ids.size();
2539 
2540  // There may be nothing to project
2541  if (!free_dofs)
2542  return;
2543 
2544  // The element matrix and RHS for projections.
2545  // Note that Ke is always real-valued, whereas
2546  // Fe may be complex valued if complex number
2547  // support is enabled
2548  DenseMatrix<Real> Ke(free_dofs, free_dofs);
2549  DenseVector<FValue> Fe(free_dofs);
2550  // The new degree of freedom coefficients to solve for
2551  DenseVector<FValue> Ufree(free_dofs);
2552 
2553  const unsigned int n_qp =
2554  cast_int<unsigned int>(xyz_values.size());
2555 
2556  // Loop over the quadrature points
2557  for (unsigned int qp=0; qp<n_qp; qp++)
2558  {
2559  // solution at the quadrature point
2560  FValue fineval = f.eval_at_point(context,
2561  var_component,
2562  xyz_values[qp],
2563  system.time);
2564  // solution grad at the quadrature point
2565  VectorValue<FValue> finegrad;
2566  if (cont == C_ONE)
2567  finegrad = g->eval_at_point(context,
2568  var_component,
2569  xyz_values[qp],
2570  system.time);
2571 
2572  // Form edge projection matrix
2573  for (unsigned int sidei=0, freei=0;
2574  sidei != n_involved_dofs; ++sidei)
2575  {
2576  unsigned int i = involved_dofs[sidei];
2577  // fixed DoFs aren't test functions
2578  if (dof_is_fixed[sidei])
2579  continue;
2580  for (unsigned int sidej=0, freej=0;
2581  sidej != n_involved_dofs; ++sidej)
2582  {
2583  unsigned int j = involved_dofs[sidej];
2584  if (dof_is_fixed[sidej])
2585  Fe(freei) -= phi[i][qp] * phi[j][qp] *
2586  JxW[qp] * Uinvolved(sidej);
2587  else
2588  Ke(freei,freej) += phi[i][qp] *
2589  phi[j][qp] * JxW[qp];
2590  if (cont == C_ONE)
2591  {
2592  if (dof_is_fixed[sidej])
2593  Fe(freei) -= ( (*dphi)[i][qp] *
2594  (*dphi)[j][qp] ) *
2595  JxW[qp] * Uinvolved(sidej);
2596  else
2597  Ke(freei,freej) += ( (*dphi)[i][qp] *
2598  (*dphi)[j][qp] )
2599  * JxW[qp];
2600  }
2601  if (!dof_is_fixed[sidej])
2602  freej++;
2603  }
2604  Fe(freei) += phi[i][qp] * fineval * JxW[qp];
2605  if (cont == C_ONE)
2606  Fe(freei) += (finegrad * (*dphi)[i][qp] ) *
2607  JxW[qp];
2608  freei++;
2609  }
2610  }
2611 
2612  Ke.cholesky_solve(Fe, Ufree);
2613 
2614  // Transfer new edge solutions to element
2615  const processor_id_type pid = node ?
2616  node->processor_id() : DofObject::invalid_processor_id;
2617  insert_ids(free_dof_ids, Ufree.get_values(), pid);
2618 }

References libMesh::C_ONE, libMesh::DenseMatrix< T >::cholesky_solve(), libMesh::FEAbstract::get_continuity(), libMesh::FEGenericBase< OutputType >::get_dphi(), libMesh::FEAbstract::get_JxW(), libMesh::FEGenericBase< OutputType >::get_phi(), libMesh::DenseVector< T >::get_values(), libMesh::FEAbstract::get_xyz(), libMesh::DofObject::invalid_processor_id, libMesh::DofObject::processor_id(), and libMesh::DenseVector< T >::size().

◆ construct_projection() [2/2]

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
void libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubProjector::construct_projection

Definition at line 2501 of file generic_projector.h.

2506 {
2507  const std::vector<Real> & JxW = fe.get_JxW();
2508  const std::vector<std::vector<Real>> & phi = fe.get_phi();
2509  const std::vector<std::vector<RealGradient>> * dphi = nullptr;
2510  const std::vector<Point> & xyz_values = fe.get_xyz();
2511  const FEContinuity cont = fe.get_continuity();
2512  const std::unordered_map<dof_id_type, FValue> & ids_to_save =
2513  this->projector.ids_to_save;
2514 
2515  if (cont == C_ONE)
2516  dphi = &(fe.get_dphi());
2517 
2518  const unsigned int n_involved_dofs =
2519  cast_int<unsigned int>(involved_dofs.size());
2520 
2521  std::vector<dof_id_type> free_dof_ids;
2522  DenseVector<FValue> Uinvolved(n_involved_dofs);
2523  std::vector<char> dof_is_fixed(n_involved_dofs, false); // bools
2524 
2525  for (auto i : IntRange<unsigned int>(0, n_involved_dofs))
2526  {
2527  const dof_id_type id = dof_indices_var[involved_dofs[i]];
2528  auto iter = ids_to_save.find(id);
2529  if (iter == ids_to_save.end())
2530  free_dof_ids.push_back(id);
2531  else
2532  {
2533  dof_is_fixed[i] = true;
2534  Uinvolved(i) = iter->second;
2535  }
2536  }
2537 
2538  const unsigned int free_dofs = free_dof_ids.size();
2539 
2540  // There may be nothing to project
2541  if (!free_dofs)
2542  return;
2543 
2544  // The element matrix and RHS for projections.
2545  // Note that Ke is always real-valued, whereas
2546  // Fe may be complex valued if complex number
2547  // support is enabled
2548  DenseMatrix<Real> Ke(free_dofs, free_dofs);
2549  DenseVector<FValue> Fe(free_dofs);
2550  // The new degree of freedom coefficients to solve for
2551  DenseVector<FValue> Ufree(free_dofs);
2552 
2553  const unsigned int n_qp =
2554  cast_int<unsigned int>(xyz_values.size());
2555 
2556  // Loop over the quadrature points
2557  for (unsigned int qp=0; qp<n_qp; qp++)
2558  {
2559  // solution at the quadrature point
2560  FValue fineval = f.eval_at_point(context,
2561  var_component,
2562  xyz_values[qp],
2563  system.time);
2564  // solution grad at the quadrature point
2565  VectorValue<FValue> finegrad;
2566  if (cont == C_ONE)
2567  finegrad = g->eval_at_point(context,
2568  var_component,
2569  xyz_values[qp],
2570  system.time);
2571 
2572  // Form edge projection matrix
2573  for (unsigned int sidei=0, freei=0;
2574  sidei != n_involved_dofs; ++sidei)
2575  {
2576  unsigned int i = involved_dofs[sidei];
2577  // fixed DoFs aren't test functions
2578  if (dof_is_fixed[sidei])
2579  continue;
2580  for (unsigned int sidej=0, freej=0;
2581  sidej != n_involved_dofs; ++sidej)
2582  {
2583  unsigned int j = involved_dofs[sidej];
2584  if (dof_is_fixed[sidej])
2585  Fe(freei) -= phi[i][qp] * phi[j][qp] *
2586  JxW[qp] * Uinvolved(sidej);
2587  else
2588  Ke(freei,freej) += phi[i][qp] *
2589  phi[j][qp] * JxW[qp];
2590  if (cont == C_ONE)
2591  {
2592  if (dof_is_fixed[sidej])
2593  Fe(freei) -= ( (*dphi)[i][qp] *
2594  (*dphi)[j][qp] ) *
2595  JxW[qp] * Uinvolved(sidej);
2596  else
2597  Ke(freei,freej) += ( (*dphi)[i][qp] *
2598  (*dphi)[j][qp] )
2599  * JxW[qp];
2600  }
2601  if (!dof_is_fixed[sidej])
2602  freej++;
2603  }
2604  Fe(freei) += phi[i][qp] * fineval * JxW[qp];
2605  if (cont == C_ONE)
2606  Fe(freei) += (finegrad * (*dphi)[i][qp] ) *
2607  JxW[qp];
2608  freei++;
2609  }
2610  }
2611 
2612  Ke.cholesky_solve(Fe, Ufree);
2613 
2614  // Transfer new edge solutions to element
2615  const processor_id_type pid = node ?
2616  node->processor_id() : DofObject::invalid_processor_id;
2617  insert_ids(free_dof_ids, Ufree.get_values(), pid);
2618 }

◆ find_dofs_to_send()

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
void libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::find_dofs_to_send ( const Node node,
const Elem elem,
unsigned short  node_num,
const var_set vars 
)
inherited

Definition at line 2345 of file generic_projector.h.

2346 {
2347  libmesh_assert (&node == elem.node_ptr(node_num));
2348 
2349  // Any ghosted node in our range might have an owner who needs our
2350  // data
2351  const processor_id_type owner = node.processor_id();
2352  if (owner != system.processor_id())
2353  {
2354  const MeshBase & mesh = system.get_mesh();
2355  const DofMap & dof_map = system.get_dof_map();
2356 
2357  // But let's check and see if we can be certain the owner can
2358  // compute any or all of its own dof coefficients on that node.
2359  std::vector<dof_id_type> node_dof_ids, patch_dof_ids;
2360  for (const auto & var : vars)
2361  {
2362  const Variable & variable = system.variable(var);
2363 
2364  if (!variable.active_on_subdomain(elem.subdomain_id()))
2365  continue;
2366 
2367  dof_map.dof_indices(elem, node_num, node_dof_ids, var);
2368  }
2369  libmesh_assert(std::is_sorted(node_dof_ids.begin(),
2370  node_dof_ids.end()));
2371  const std::vector<dof_id_type> & patch =
2372  (*this->projector.nodes_to_elem)[node.id()];
2373  for (const auto & elem_id : patch)
2374  {
2375  const Elem & patch_elem = mesh.elem_ref(elem_id);
2376  if (!patch_elem.active() || owner != patch_elem.processor_id())
2377  continue;
2378  dof_map.dof_indices(&patch_elem, patch_dof_ids);
2379  std::sort(patch_dof_ids.begin(), patch_dof_ids.end());
2380 
2381  // Remove any node_dof_ids that we see can be calculated on
2382  // this element
2383  std::vector<dof_id_type> diff_ids(node_dof_ids.size());
2384  auto it = std::set_difference(node_dof_ids.begin(), node_dof_ids.end(),
2385  patch_dof_ids.begin(), patch_dof_ids.end(), diff_ids.begin());
2386  diff_ids.resize(it-diff_ids.begin());
2387  node_dof_ids.swap(diff_ids);
2388  if (node_dof_ids.empty())
2389  break;
2390  }
2391 
2392  // Give ids_to_push default invalid pid: not yet computed
2393  for (auto id : node_dof_ids)
2395  }
2396 }

References libMesh::Elem::active(), libMesh::Variable::active_on_subdomain(), libMesh::DofMap::dof_indices(), libMesh::MeshBase::elem_ref(), libMesh::DofObject::id(), libMesh::DofObject::invalid_processor_id, libMesh::Parallel::Utils::is_sorted(), libMesh::libmesh_assert(), mesh, libMesh::Elem::node_ptr(), libMesh::DofObject::processor_id(), and libMesh::Elem::subdomain_id().

◆ insert_id() [1/2]

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
void libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::insert_id ( dof_id_type  id,
const FValue &  val,
processor_id_type  pid 
)
inherited

Definition at line 1117 of file generic_projector.h.

1118 {
1119  auto iter = new_ids_to_push.find(id);
1120  if (iter == new_ids_to_push.end())
1121  action.insert(id, val);
1122  else
1123  {
1125  iter->second = std::make_pair(val, pid);
1126  }
1127  if (!this->projector.done_saving_ids)
1128  {
1129  libmesh_assert(!new_ids_to_save.count(id));
1130  new_ids_to_save[id] = val;
1131  }
1132 }

References libMesh::DofObject::invalid_processor_id, and libMesh::libmesh_assert().

◆ insert_id() [2/2]

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
void libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::insert_id

Definition at line 1117 of file generic_projector.h.

1118 {
1119  auto iter = new_ids_to_push.find(id);
1120  if (iter == new_ids_to_push.end())
1121  action.insert(id, val);
1122  else
1123  {
1125  iter->second = std::make_pair(val, pid);
1126  }
1127  if (!this->projector.done_saving_ids)
1128  {
1129  libmesh_assert(!new_ids_to_save.count(id));
1130  new_ids_to_save[id] = val;
1131  }
1132 }

◆ insert_ids() [1/2]

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
void libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::insert_ids ( const std::vector< dof_id_type > &  ids,
const std::vector< FValue > &  vals,
processor_id_type  pid 
)
inherited

Definition at line 1138 of file generic_projector.h.

1139 {
1140  libmesh_assert_equal_to(ids.size(), vals.size());
1141  for (auto i : index_range(ids))
1142  {
1143  const dof_id_type id = ids[i];
1144  const FValue & val = vals[i];
1145 
1146  auto iter = new_ids_to_push.find(id);
1147  if (iter == new_ids_to_push.end())
1148  action.insert(id, val);
1149  else
1150  {
1152  iter->second = std::make_pair(val, pid);
1153  }
1154  if (!this->projector.done_saving_ids)
1155  {
1156  libmesh_assert(!new_ids_to_save.count(id));
1157  new_ids_to_save[id] = val;
1158  }
1159  }
1160 }

References libMesh::index_range(), libMesh::DofObject::invalid_processor_id, and libMesh::libmesh_assert().

◆ insert_ids() [2/2]

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
void libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::insert_ids

Definition at line 1138 of file generic_projector.h.

1139 {
1140  libmesh_assert_equal_to(ids.size(), vals.size());
1141  for (auto i : index_range(ids))
1142  {
1143  const dof_id_type id = ids[i];
1144  const FValue & val = vals[i];
1145 
1146  auto iter = new_ids_to_push.find(id);
1147  if (iter == new_ids_to_push.end())
1148  action.insert(id, val);
1149  else
1150  {
1152  iter->second = std::make_pair(val, pid);
1153  }
1154  if (!this->projector.done_saving_ids)
1155  {
1156  libmesh_assert(!new_ids_to_save.count(id));
1157  new_ids_to_save[id] = val;
1158  }
1159  }
1160 }

◆ join()

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
void libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::join ( const SubFunctor other)
inherited

Definition at line 1166 of file generic_projector.h.

1167 {
1168  new_ids_to_push.insert(other.new_ids_to_push.begin(), other.new_ids_to_push.end());
1169  new_ids_to_save.insert(other.new_ids_to_save.begin(), other.new_ids_to_save.end());
1170 }

References libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::new_ids_to_push, and libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::new_ids_to_save.

◆ operator()()

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
void libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::ProjectVertices::operator() ( const node_range range)

Definition at line 1655 of file generic_projector.h.

1656 {
1657  LOG_SCOPE ("project_vertices","GenericProjector");
1658 
1659  const unsigned int sys_num = system.number();
1660 
1661  // Variables with extra hanging dofs can't safely use eval_at_node
1662  // in as many places as variables without can.
1663  std::vector<unsigned short> extra_hanging_dofs;
1664  for (auto v_num : this->projector.variables)
1665  {
1666  if (extra_hanging_dofs.size() <= v_num)
1667  extra_hanging_dofs.resize(v_num+1, false);
1668  extra_hanging_dofs[v_num] =
1670  }
1671 
1672  for (const auto & v_pair : range)
1673  {
1674  const Node & vertex = *v_pair.first;
1675  const Elem & elem = *std::get<0>(v_pair.second);
1676  const unsigned int n = std::get<1>(v_pair.second);
1677  const var_set & vertex_vars = std::get<2>(v_pair.second);
1678 
1679  context.pre_fe_reinit(system, &elem);
1680 
1681  this->find_dofs_to_send(vertex, elem, n, vertex_vars);
1682 
1683  // Look at all the variables we're supposed to interpolate from
1684  // this element on this vertex
1685  for (const auto & var : vertex_vars)
1686  {
1687  const Variable & variable = system.variable(var);
1688  const FEType & base_fe_type = variable.type();
1689  const unsigned int var_component =
1691 
1692  if (base_fe_type.family == SCALAR)
1693  continue;
1694 
1695  const FEContinuity & cont = this->conts[var];
1696  if (cont == DISCONTINUOUS)
1697  {
1698  libmesh_assert_equal_to(vertex.n_comp(sys_num, var), 0);
1699  }
1700  else if (cont == C_ZERO)
1701  {
1702  libmesh_assert(vertex.n_comp(sys_num, var));
1703  const dof_id_type id = vertex.dof_number(sys_num, var, 0);
1704  // C_ZERO elements have a single nodal value DoF at vertices
1705  const FValue val = f.eval_at_node
1706  (context, var_component, /*dim=*/ 0, // Don't care w/C0
1707  vertex, extra_hanging_dofs[var], system.time);
1708  insert_id(id, val, vertex.processor_id());
1709  }
1710  else if (cont == C_ONE)
1711  {
1712  libmesh_assert(vertex.n_comp(sys_num, var));
1713  const dof_id_type first_id = vertex.dof_number(sys_num, var, 0);
1714 
1715  // C_ONE elements have a single nodal value and dim
1716  // gradient values at vertices, as well as cross
1717  // gradients for HERMITE. We need to have an element in
1718  // hand to figure out dim and to have in case this
1719  // vertex is a new vertex.
1720  const int dim = elem.dim();
1721 #ifndef NDEBUG
1722  // For now all C1 elements at a vertex had better have
1723  // the same dimension. If anyone hits these asserts let
1724  // me know; we could probably support a mixed-dimension
1725  // mesh IFF the 2D elements were all parallel to xy and
1726  // the 1D elements all parallel to x.
1727  for (const auto e_id : (*this->projector.nodes_to_elem)[vertex.id()])
1728  {
1729  const Elem & e = system.get_mesh().elem_ref(e_id);
1730  libmesh_assert_equal_to(dim, e.dim());
1731  }
1732 #endif
1733 #ifdef LIBMESH_ENABLE_AMR
1734  bool is_parent_vertex = false;
1735  if (elem.parent())
1736  {
1737  const int i_am_child =
1738  elem.parent()->which_child_am_i(&elem);
1739  is_parent_vertex =
1740  elem.parent()->is_vertex_on_parent(i_am_child, n);
1741  }
1742 #else
1743  const bool is_parent_vertex = false;
1744 #endif
1745 
1746  // The hermite element vertex shape functions are weird
1747  if (base_fe_type.family == HERMITE)
1748  {
1749  const FValue val =
1750  f.eval_at_node(context,
1751  var_component,
1752  dim,
1753  vertex,
1754  extra_hanging_dofs[var],
1755  system.time);
1756  insert_id(first_id, val, vertex.processor_id());
1757 
1758  VectorValue<FValue> grad =
1759  is_parent_vertex ?
1760  g->eval_at_node(context,
1761  var_component,
1762  dim,
1763  vertex,
1764  extra_hanging_dofs[var],
1765  system.time) :
1766  g->eval_at_point(context,
1767  var_component,
1768  vertex,
1769  system.time);
1770  // x derivative
1771  insert_id(first_id+1, grad(0),
1772  vertex.processor_id());
1773 #if LIBMESH_DIM > 1
1774  if (dim > 1)
1775  {
1776  // We'll finite difference mixed derivatives
1777  Real delta_x = TOLERANCE * elem.hmin();
1778 
1779  Point nxminus = elem.point(n),
1780  nxplus = elem.point(n);
1781  nxminus(0) -= delta_x;
1782  nxplus(0) += delta_x;
1783  VectorValue<FValue> gxminus =
1784  g->eval_at_point(context,
1785  var_component,
1786  nxminus,
1787  system.time);
1788  VectorValue<FValue> gxplus =
1789  g->eval_at_point(context,
1790  var_component,
1791  nxplus,
1792  system.time);
1793  // y derivative
1794  insert_id(first_id+2, grad(1),
1795  vertex.processor_id());
1796  // xy derivative
1797  insert_id(first_id+3,
1798  (gxplus(1) - gxminus(1)) / 2. / delta_x,
1799  vertex.processor_id());
1800 
1801 #if LIBMESH_DIM > 2
1802  if (dim > 2)
1803  {
1804  // z derivative
1805  insert_id(first_id+4, grad(2),
1806  vertex.processor_id());
1807  // xz derivative
1808  insert_id(first_id+5,
1809  (gxplus(2) - gxminus(2)) / 2. / delta_x,
1810  vertex.processor_id());
1811 
1812  // We need new points for yz
1813  Point nyminus = elem.point(n),
1814  nyplus = elem.point(n);
1815  nyminus(1) -= delta_x;
1816  nyplus(1) += delta_x;
1817  VectorValue<FValue> gyminus =
1818  g->eval_at_point(context,
1819  var_component,
1820  nyminus,
1821  system.time);
1822  VectorValue<FValue> gyplus =
1823  g->eval_at_point(context,
1824  var_component,
1825  nyplus,
1826  system.time);
1827  // yz derivative
1828  insert_id(first_id+6,
1829  (gyplus(2) - gyminus(2)) / 2. / delta_x,
1830  vertex.processor_id());
1831  // Getting a 2nd order xyz is more tedious
1832  Point nxmym = elem.point(n),
1833  nxmyp = elem.point(n),
1834  nxpym = elem.point(n),
1835  nxpyp = elem.point(n);
1836  nxmym(0) -= delta_x;
1837  nxmym(1) -= delta_x;
1838  nxmyp(0) -= delta_x;
1839  nxmyp(1) += delta_x;
1840  nxpym(0) += delta_x;
1841  nxpym(1) -= delta_x;
1842  nxpyp(0) += delta_x;
1843  nxpyp(1) += delta_x;
1844  VectorValue<FValue> gxmym =
1845  g->eval_at_point(context,
1846  var_component,
1847  nxmym,
1848  system.time);
1849  VectorValue<FValue> gxmyp =
1850  g->eval_at_point(context,
1851  var_component,
1852  nxmyp,
1853  system.time);
1854  VectorValue<FValue> gxpym =
1855  g->eval_at_point(context,
1856  var_component,
1857  nxpym,
1858  system.time);
1859  VectorValue<FValue> gxpyp =
1860  g->eval_at_point(context,
1861  var_component,
1862  nxpyp,
1863  system.time);
1864  FValue gxzplus = (gxpyp(2) - gxmyp(2))
1865  / 2. / delta_x;
1866  FValue gxzminus = (gxpym(2) - gxmym(2))
1867  / 2. / delta_x;
1868  // xyz derivative
1869  insert_id(first_id+7,
1870  (gxzplus - gxzminus) / 2. / delta_x,
1871  vertex.processor_id());
1872  }
1873 #endif // LIBMESH_DIM > 2
1874  }
1875 #endif // LIBMESH_DIM > 1
1876  }
1877  else
1878  {
1879  // Currently other C_ONE elements have a single nodal
1880  // value shape function and nodal gradient component
1881  // shape functions
1882  libmesh_assert_equal_to
1884  (dim, base_fe_type, elem.type(),
1885  elem.get_node_index(&vertex)),
1886  (unsigned int)(1 + dim));
1887  const FValue val =
1888  f.eval_at_node(context, var_component, dim,
1889  vertex, extra_hanging_dofs[var],
1890  system.time);
1891  insert_id(first_id, val, vertex.processor_id());
1892  VectorValue<FValue> grad =
1893  is_parent_vertex ?
1894  g->eval_at_node(context, var_component, dim,
1895  vertex, extra_hanging_dofs[var],
1896  system.time) :
1897  g->eval_at_point(context, var_component, vertex,
1898  system.time);
1899  for (int i=0; i!= dim; ++i)
1900  insert_id(first_id + i + 1, grad(i),
1901  vertex.processor_id());
1902  }
1903  }
1904  else
1905  libmesh_error_msg("Unknown continuity " << cont);
1906  }
1907  }
1908 }

References libMesh::C_ONE, libMesh::C_ZERO, dim, libMesh::Elem::dim(), libMesh::DISCONTINUOUS, libMesh::DofObject::dof_number(), libMesh::FEInterface::extra_hanging_dofs(), libMesh::FEType::family, libMesh::Elem::get_node_index(), libMesh::HERMITE, libMesh::Elem::hmin(), libMesh::DofObject::id(), libMesh::Elem::is_vertex_on_parent(), libMesh::libmesh_assert(), libMesh::DofObject::n_comp(), libMesh::FEInterface::n_dofs_at_node(), libMesh::Elem::parent(), libMesh::Elem::point(), libMesh::DofObject::processor_id(), libMesh::Real, libMesh::SCALAR, libMesh::TOLERANCE, libMesh::Variable::type(), libMesh::Elem::type(), and libMesh::Elem::which_child_am_i().

Member Data Documentation

◆ action

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
ProjectionAction libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::action

Definition at line 193 of file generic_projector.h.

◆ context

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
FEMContext libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::context

Definition at line 198 of file generic_projector.h.

◆ conts

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
std::vector<FEContinuity> libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::conts

Definition at line 201 of file generic_projector.h.

◆ f

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
FFunctor libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::f

Definition at line 194 of file generic_projector.h.

◆ g

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
std::unique_ptr<GFunctor> libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubProjector::g

Definition at line 227 of file generic_projector.h.

◆ new_ids_to_push

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
std::unordered_map<dof_id_type, std::pair<FValue, processor_id_type> > libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::new_ids_to_push
inherited

◆ new_ids_to_save

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
std::unordered_map<dof_id_type, FValue> libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::new_ids_to_save
inherited

◆ projector

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
GenericProjector& libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::projector
inherited

Definition at line 154 of file generic_projector.h.

◆ system

template<typename FFunctor , typename GFunctor , typename FValue , typename ProjectionAction >
const System& libMesh::GenericProjector< FFunctor, GFunctor, FValue, ProjectionAction >::SubFunctor::system

Definition at line 203 of file generic_projector.h.


The documentation for this struct was generated from the following file:
libMesh::C_ONE
Definition: enum_fe_family.h:80
libMesh::dof_id_type
uint8_t dof_id_type
Definition: id_types.h:67
libMesh::GenericProjector::SubFunctor::new_ids_to_save
std::unordered_map< dof_id_type, FValue > new_ids_to_save
Definition: generic_projector.h:169
libMesh::FEInterface::extra_hanging_dofs
static bool extra_hanging_dofs(const FEType &fe_t)
Definition: fe_interface.C:1656
libMesh::GenericProjector::var_set
std::set< unsigned int > var_set
Definition: generic_projector.h:149
libMesh::HERMITE
Definition: enum_fe_family.h:54
libMesh::FEInterface::n_dofs_at_node
static unsigned int n_dofs_at_node(const unsigned int dim, const FEType &fe_t, const ElemType t, const unsigned int n)
Definition: fe_interface.C:503
libMesh::GenericProjector::SubFunctor::insert_id
void insert_id(dof_id_type id, const FValue &val, processor_id_type pid)
Definition: generic_projector.h:1117
libMesh::MeshBase::elem_ref
virtual const Elem & elem_ref(const dof_id_type i) const
Definition: mesh_base.h:521
libMesh::index_range
IntRange< std::size_t > index_range(const std::vector< T > &vec)
Helper function that returns an IntRange<std::size_t> representing all the indices of the passed-in v...
Definition: int_range.h:106
libMesh::FEMContext::pre_fe_reinit
virtual void pre_fe_reinit(const System &, const Elem *e)
Reinitializes local data vectors/matrices on the current geometric element.
Definition: fem_context.C:1642
libMesh::TOLERANCE
static const Real TOLERANCE
Definition: libmesh_common.h:128
libMesh::System::number
unsigned int number() const
Definition: system.h:2075
libMesh::Variable::type
const FEType & type() const
Definition: variable.h:119
mesh
MeshBase & mesh
Definition: mesh_communication.C:1257
libMesh::GenericProjector::SubFunctor::new_ids_to_push
std::unordered_map< dof_id_type, std::pair< FValue, processor_id_type > > new_ids_to_push
Definition: generic_projector.h:165
libMesh::System::variable
const Variable & variable(unsigned int var) const
Return a constant reference to Variable var.
Definition: system.h:2183
libMesh::GenericProjector::SubProjector::SubProjector
SubProjector(GenericProjector &p)
Definition: generic_projector.h:1096
libMesh::Parallel::Utils::is_sorted
bool is_sorted(const std::vector< KeyType > &v)
Definition: parallel_conversion_utils.h:52
dim
unsigned int dim
Definition: adaptivity_ex3.C:113
libMesh::GenericProjector::SubFunctor::conts
std::vector< FEContinuity > conts
Definition: generic_projector.h:201
libMesh::libmesh_assert
libmesh_assert(ctx)
libMesh::GenericProjector::SubFunctor::insert_ids
void insert_ids(const std::vector< dof_id_type > &ids, const std::vector< FValue > &vals, processor_id_type pid)
Definition: generic_projector.h:1138
libMesh::GenericProjector::SubFunctor::find_dofs_to_send
void find_dofs_to_send(const Node &node, const Elem &elem, unsigned short node_num, const var_set &vars)
Definition: generic_projector.h:2345
libMesh::GenericProjector::done_saving_ids
bool done_saving_ids
Definition: generic_projector.h:93
libMesh::GenericProjector::SubFunctor::context
FEMContext context
Definition: generic_projector.h:198
libMesh::System::variable_scalar_number
unsigned int variable_scalar_number(const std::string &var, unsigned int component) const
Definition: system.h:2214
libMesh::System::get_mesh
const MeshBase & get_mesh() const
Definition: system.h:2083
libMesh::ParallelObject::processor_id
processor_id_type processor_id() const
Definition: parallel_object.h:106
libMesh::processor_id_type
uint8_t processor_id_type
Definition: id_types.h:104
libMesh::DISCONTINUOUS
Definition: enum_fe_family.h:78
libMesh::C_ZERO
Definition: enum_fe_family.h:79
libMesh::GenericProjector::nodes_to_elem
std::unordered_map< dof_id_type, std::vector< dof_id_type > > * nodes_to_elem
Definition: generic_projector.h:92
libMesh::System::time
Real time
For time-dependent problems, this is the time t at the beginning of the current timestep.
Definition: system.h:1561
libMesh::Elem::parent
const Elem * parent() const
Definition: elem.h:2434
libMesh::DofObject::invalid_processor_id
static const processor_id_type invalid_processor_id
An invalid processor_id to distinguish DoFs that have not been assigned to a processor.
Definition: dof_object.h:432
libMesh::GenericProjector::SubFunctor::action
ProjectionAction action
Definition: generic_projector.h:193
libMesh::GenericProjector::SubFunctor::projector
GenericProjector & projector
Definition: generic_projector.h:154
libMesh::GenericProjector::ids_to_save
std::unordered_map< dof_id_type, FValue > ids_to_save
Definition: generic_projector.h:145
libMesh::System::get_dof_map
const DofMap & get_dof_map() const
Definition: system.h:2099
libMesh::GenericProjector::SubFunctor::f
FFunctor f
Definition: generic_projector.h:194
libMesh::SCALAR
Definition: enum_fe_family.h:58
libMesh::GenericProjector::SubFunctor::system
const System & system
Definition: generic_projector.h:203
libMesh::Real
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
Definition: libmesh_common.h:121
libMesh::GenericProjector::variables
const std::vector< unsigned int > & variables
Definition: generic_projector.h:91
libMesh::FEContinuity
FEContinuity
Definition: enum_fe_family.h:77
libMesh::Elem::which_child_am_i
unsigned int which_child_am_i(const Elem *e) const
Definition: elem.h:2596
libMesh::GenericProjector::SubProjector::g
std::unique_ptr< GFunctor > g
Definition: generic_projector.h:227