19#include "libmesh/quadrature.h"
20#include "libmesh/elem_side_builder.h"
33 MooseEnum system_enum(
"ALL=-1 NL AUX",
"ALL");
37 "The system(s) to retrieve the number of DOFs from (NL, AUX, ALL). Default == ALL");
39 params.
addParam<
bool>(
"sync_to_all_procs",
41 "Whether or not to sync the vectors to all processors. By default we only "
42 "sync them to processor 0 so they can be written out. Setting this to "
43 "true will use more communication, but is necessary if you expect these "
44 "vectors to be available on all processors");
47 "num_elems=0 num_nodes=1 num_dofs=2 num_partition_sides=3 partition_surface_area=4 "
48 "num_partition_hardware_id_sides=5 partition_hardware_id_surface_area=6",
49 "num_elems num_nodes num_dofs num_partition_sides partition_surface_area "
50 "num_partition_hardware_id_sides partition_hardware_id_surface_area");
52 "balances", balances,
"Which metrics do you want to use to represent word balance");
59 _rank_map(_app.rankMap()),
60 _my_hardware_id(_rank_map.hardwareID(processor_id())),
61 _sync_to_all_procs(getParam<bool>(
"sync_to_all_procs")),
65 _local_num_partition_sides(0),
66 _local_partition_surface_area(0),
67 _local_num_partition_hardware_id_sides(0),
68 _local_partition_hardware_id_surface_area(0),
69 _pid(declareVector(
"pid")),
100 _my_hardware_id(rank_map.hardwareID(
mesh.processor_id())),
103 _local_num_partition_sides(0),
104 _local_partition_surface_area(0),
105 _local_num_partition_hardware_id_sides(0),
106 _local_partition_hardware_id_surface_area(0),
107 _this_pid(_mesh.processor_id())
116 _rank_map(x._rank_map),
117 _my_hardware_id(x._my_hardware_id),
120 _local_num_partition_sides(0),
121 _local_partition_surface_area(0),
122 _local_num_partition_hardware_id_sides(0),
123 _local_partition_hardware_id_surface_area(0),
124 _this_pid(x._this_pid),
125 _petsc_partitioner(x._petsc_partitioner)
129 virtual ~WBElementLoop() {}
131 virtual void pre()
override
133 _local_num_elems = 0;
135 _local_num_partition_sides = 0;
136 _local_partition_surface_area = 0;
137 _local_num_partition_hardware_id_sides = 0;
138 _local_partition_hardware_id_surface_area = 0;
141 virtual void onElement(
const Elem * elem)
override
143 if (_petsc_partitioner && _petsc_partitioner->applyElementWeight())
147 _local_num_elems += _petsc_partitioner->computeElementWeight(
const_cast<Elem &
>(*elem));
155 auto n_sys = elem->n_systems();
156 for (
decltype(n_sys) sys = 0; sys < n_sys; sys++)
158 auto n_vars = elem->n_vars(sys);
160 for (
decltype(n_vars) var = 0; var <
n_vars; var++)
161 _local_num_dofs += elem->n_dofs(sys, var);
166 auto n_vars = elem->n_vars(
static_cast<unsigned int>(_system));
168 for (
decltype(n_vars) var = 0; var <
n_vars; var++)
169 _local_num_dofs += elem->n_dofs(
static_cast<unsigned int>(_system), var);
173 virtual void onInternalSide(
const Elem * elem,
unsigned int side)
override
175 if (elem->neighbor_ptr(side)->processor_id() != _this_pid)
177 if (_petsc_partitioner && _petsc_partitioner->applySideWeight())
181 _local_num_partition_sides +=
182 _petsc_partitioner->computeSideWeight(
const_cast<Elem &
>(*elem), side);
185 _local_num_partition_sides++;
189 auto volume = _elem_side_builder(*elem, side).volume();
190 _local_partition_surface_area +=
volume;
192 if (_my_hardware_id != _rank_map.hardwareID(elem->neighbor_ptr(side)->processor_id()))
194 _local_num_partition_hardware_id_sides++;
195 _local_partition_hardware_id_surface_area +=
volume;
200 void join(
const WBElementLoop & y)
202 _local_num_elems += y._local_num_elems;
203 _local_num_dofs += y._local_num_dofs;
204 _local_num_partition_sides += y._local_num_partition_sides;
205 _local_partition_surface_area += y._local_partition_surface_area;
206 _local_num_partition_hardware_id_sides += y._local_num_partition_hardware_id_sides;
207 _local_partition_hardware_id_surface_area += y._local_partition_hardware_id_surface_area;
214 unsigned int _my_hardware_id;
219 Real _local_partition_surface_area;
220 dof_id_type _local_num_partition_hardware_id_sides;
221 Real _local_partition_hardware_id_surface_area;
230 bool shouldComputeInternalSide(
const Elem & ,
const Elem & )
const override
236class WBNodeLoop :
public ThreadedNodeLoop<ConstNodeRange, ConstNodeRange::const_iterator>
255 virtual void onNode(ConstNodeRange::const_iterator & node_it)
257 auto & node = *(*node_it);
264 auto n_sys = node.n_systems();
265 for (
decltype(n_sys) sys = 0; sys < n_sys; sys++)
267 auto n_vars = node.n_vars(sys);
269 for (
decltype(n_vars) var = 0; var <
n_vars; var++)
270 _local_num_dofs += node.n_dofs(sys, var);
275 auto n_vars = node.n_vars(
static_cast<unsigned int>(_system));
277 for (
decltype(n_vars) var = 0; var <
n_vars; var++)
278 _local_num_dofs += node.n_dofs(
static_cast<unsigned int>(_system), var);
282 void join(WBNodeLoop & y)
284 _local_num_nodes += y._local_num_nodes;
285 _local_num_dofs += y._local_num_dofs;
351 mooseError(
"Unknown balance type: ", balance_id);
380 mooseError(
"Unknown balance type: ", balance_id);
390 auto balance_id = balance.id();
394 gather(balance_id, balance_vector);
398 std::iota(
_pid.begin(),
_pid.end(), 0);
void mooseError(Args &&... args)
Emit an error message with the given stringified, concatenated args and terminate the application.
std::vector< Real > VectorPostprocessorValue
registerMooseObject("MooseApp", WorkBalance)
Specialization of SubProblem for solving nonlinear equations plus auxiliary equations.
virtual MooseMesh & mesh() override
This class is here to combine the VectorPostprocessor interface and the base class VectorPostprocesso...
static InputParameters validParams()
This is a "smart" enum class intended to replace many of the shortcomings in the C++ enum type It sho...
MooseMesh wraps a libMesh::Mesh object and enhances its capabilities by caching additional data and s...
This is a "smart" enum class intended to replace many of the shortcomings in the C++ enum type.
Partitions a mesh using external petsc partitioners such as parmetis, ptscotch, chaco,...
Builds lists and maps that help in knowing which physical hardware nodes each rank is on.
processor_id_type size() const
void gather(const unsigned int root_id, const T &send_data, std::vector< T, A > &recv) const
void allgather(const T &send_data, std::vector< T, A > &recv_data) const
Base class for assembly-like calculations.
FEProblemBase & _fe_problem
Reference to the FEProblemBase for this user object.
VectorPostprocessorValue & declareVector(const std::string &vector_name)
Register a new vector to fill up.
Compute several metrics for each MPI process.
void gather(int balance_id, VectorPostprocessorValue &vppv)
std::map< std::string, VectorPostprocessorValue * > _balance_vectors
The VPP vectors that will hold the balance metrics.
WorkBalance(const InputParameters ¶meters)
dof_id_type _local_num_nodes
const RankMap & _rank_map
Helpful in determining the physical layout of the ranks.
VectorPostprocessorValue & _pid
virtual void finalize() override
Finalize.
MultiMooseEnum _balances
The chosen balance metrics to compute.
dof_id_type _local_num_partition_hardware_id_sides
static InputParameters validParams()
int _system
The system to count DoFs from.
dof_id_type _local_num_elems
dof_id_type _local_num_dofs
virtual void execute() override
Execute method.
virtual void initialize() override
Called before execute() is ever called so that data can be cleared.
Real _local_partition_hardware_id_surface_area
dof_id_type _local_num_partition_sides
Real _local_partition_surface_area
const Parallel::Communicator & _communicator
std::string toLower(std::string name)
Convert supplied string to lower case.
uint8_t processor_id_type
void parallel_reduce(const Range &range, Body &body, unsigned int n_threads=libMesh::n_threads())
StoredRange< MeshBase::const_node_iterator, const Node * > ConstNodeRange
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real