13#include "libmesh/string_to_enum.h"
14#include "libmesh/mesh_tools.h"
15#include "libmesh/parallel_sync.h"
22 "Base class to compute K_ij (a measure of advective flux from node i to node j) "
23 "and R+ and R- (which quantify amount of antidiffusion to add) in the "
24 "Kuzmin-Turek FEM-TVD multidimensional scheme");
25 MooseEnum flux_limiter_type(
"MinMod VanLeer MC superbee None",
"VanLeer");
28 "Type of flux limiter to use. 'None' means that no antidiffusion "
29 "will be added in the Kuzmin-Turek scheme");
31 "allowable_MB_wastage",
33 "allowable_MB_wastage > 0.0",
34 "This object will issue a memory warning if the internal node-numbering data structure "
35 "wastes more than allowable_MB_wastage megabytes. This data structure uses sequential "
36 "node-numbering which is optimized for speed rather than memory efficiency");
39 Moose::RelationshipManagerType::GEOMETRIC |
40 Moose::RelationshipManagerType::ALGEBRAIC |
41 Moose::RelationshipManagerType::COUPLING,
43 { rm_params.
set<
unsigned short>(
"layers") = 2; });
51 _resizing_needed(true),
59 _u_nodal_computed_by_thread(),
62 _my_pid(processor_id()),
67 _allowable_MB_wastage(getParam<Real>(
"allowable_MB_wastage"))
72 "The AdvectiveFluxCalculator UserObject " +
name() +
73 " execute_on parameter must include, at least, 'linear'. This is to ensure that "
74 "this UserObject computes all necessary quantities just before the Kernels evaluate "
96 if (this->
hasBlocks(elem->subdomain_id()))
97 for (
unsigned i = 0; i < elem->n_nodes(); ++i)
101 if (this->
hasBlocks(elem->subdomain_id()))
102 for (
unsigned i = 0; i < elem->n_nodes(); ++i)
103 for (
unsigned j = 0; j < elem->n_nodes(); ++j)
113 "In at least one processor, the sequential node-numbering internal data structure used "
115 name() +
" is using memory inefficiently.\nThe memory wasted is " +
117 " megabytes.\n The node-numbering data structure has been optimized for speed at the "
118 "expense of memory, but that may not be an appropriate optimization for your case, "
119 "because the node numbering is not close to sequential in your case.\n");
123 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
124 _kij[sequential_i].assign(
140 if (this->
hasBlocks(elem->subdomain_id()))
141 for (
unsigned i = 0; i < elem->n_nodes(); ++i)
143 const dof_id_type node_i = elem->node_id(i);
152 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
155 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
157 const std::vector<dof_id_type> con_i =
159 const std::size_t num_con_i = con_i.size();
161 for (std::size_t j = 0; j < con_i.size(); ++j)
163 const dof_id_type sequential_j = con_i[j];
164 const std::size_t num_con_j =
210 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
232 for (
unsigned qp = 0; qp <
_qrule->n_points(); ++qp)
240 dof_id_type global_i, dof_id_type global_j,
unsigned local_i,
unsigned local_j,
unsigned qp)
253 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
255 const std::size_t num_con_i =
257 for (std::size_t j = 0; j < num_con_i; ++j)
258 _kij[sequential_i][j] += afc._kij[sequential_i][j];
262 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
264 _u_nodal[sequential_i] = afc._u_nodal[sequential_i];
282 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
284 const std::vector<dof_id_type> & con_i =
286 const std::size_t num_con_i = con_i.size();
287 _dij[sequential_i].assign(num_con_i, 0.0);
288 _dDij_dKij[sequential_i].assign(num_con_i, 0.0);
289 _dDij_dKji[sequential_i].assign(num_con_i, 0.0);
290 _dDii_dKij[sequential_i].assign(num_con_i, 0.0);
291 _dDii_dKji[sequential_i].assign(num_con_i, 0.0);
292 const unsigned index_i_to_i =
294 for (std::size_t j = 0; j < num_con_i; ++j)
296 const dof_id_type sequential_j = con_i[j];
297 if (sequential_i == sequential_j)
299 const unsigned index_j_to_i =
301 const Real kij =
_kij[sequential_i][j];
302 const Real kji =
_kij[sequential_j][index_j_to_i];
303 if ((kij <= kji) && (kij < 0.0))
305 _dij[sequential_i][j] = -kij;
309 else if ((kji <= kij) && (kji < 0.0))
311 _dij[sequential_i][j] = -kji;
316 _dij[sequential_i][j] = 0.0;
317 _dij[sequential_i][index_i_to_i] -=
_dij[sequential_i][j];
323 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
325 const std::vector<dof_id_type> & con_i =
327 const std::size_t num_con_i = con_i.size();
328 _lij[sequential_i].assign(num_con_i, 0.0);
329 for (std::size_t j = 0; j < num_con_i; ++j)
330 _lij[sequential_i][j] =
_kij[sequential_i][j] +
_dij[sequential_i][j];
335 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
344 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
346 const std::vector<dof_id_type> & con_i =
348 const unsigned num_con_i = con_i.size();
349 _fa[sequential_i].assign(num_con_i, 0.0);
350 _dfa[sequential_i].resize(num_con_i);
353 for (std::size_t j = 0; j < num_con_i; ++j)
355 for (
const auto & global_k : con_i)
356 _dfa[sequential_i][j][global_k] = 0;
357 const dof_id_type global_j = con_i[j];
359 const unsigned num_con_j = con_j.size();
360 for (
const auto & global_k : con_j)
361 _dfa[sequential_i][j][global_k] = 0;
362 _dFij_dKik[sequential_i][j].assign(num_con_i, 0.0);
363 _dFij_dKjk[sequential_i][j].assign(num_con_j, 0.0);
367 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
370 const Real u_i =
_u_nodal[sequential_i];
371 const std::vector<dof_id_type> & con_i =
373 const std::size_t num_con_i = con_i.size();
374 for (std::size_t j = 0; j < num_con_i; ++j)
376 const dof_id_type sequential_j = con_i[j];
377 if (sequential_i == sequential_j)
379 const unsigned index_j_to_i =
381 const Real Lij =
_lij[sequential_i][j];
382 const Real Lji =
_lij[sequential_j][index_j_to_i];
385 const Real Dij =
_dij[sequential_i][j];
387 const Real u_j =
_u_nodal[sequential_j];
388 Real prefactor = 0.0;
389 std::vector<Real> dprefactor_du(num_con_i,
391 std::vector<Real> dprefactor_dKij(
393 Real dprefactor_dKji = 0;
396 if (Lji <=
_rP[sequential_i] * Dij)
399 dprefactor_dKij[j] +=
_dDij_dKji[sequential_j][index_j_to_i];
400 dprefactor_dKji += 1.0 +
_dDij_dKij[sequential_j][index_j_to_i];
404 prefactor =
_rP[sequential_i] * Dij;
405 for (std::size_t ind_j = 0; ind_j < num_con_i; ++ind_j)
406 dprefactor_du[ind_j] =
_drP[sequential_i][ind_j] * Dij;
407 dprefactor_dKij[j] +=
_rP[sequential_i] *
_dDij_dKij[sequential_i][j];
408 dprefactor_dKji +=
_rP[sequential_i] *
_dDij_dKji[sequential_i][j];
409 for (std::size_t ind_j = 0; ind_j < num_con_i; ++ind_j)
410 dprefactor_dKij[ind_j] +=
_drP_dk[sequential_i][ind_j] * Dij;
415 if (Lji <=
_rM[sequential_i] * Dij)
418 dprefactor_dKij[j] +=
_dDij_dKji[sequential_j][index_j_to_i];
419 dprefactor_dKji += 1.0 +
_dDij_dKij[sequential_j][index_j_to_i];
423 prefactor =
_rM[sequential_i] * Dij;
424 for (std::size_t ind_j = 0; ind_j < num_con_i; ++ind_j)
425 dprefactor_du[ind_j] =
_drM[sequential_i][ind_j] * Dij;
426 dprefactor_dKij[j] +=
_rM[sequential_i] *
_dDij_dKij[sequential_i][j];
427 dprefactor_dKji +=
_rM[sequential_i] *
_dDij_dKji[sequential_i][j];
428 for (std::size_t ind_j = 0; ind_j < num_con_i; ++ind_j)
429 dprefactor_dKij[ind_j] +=
_drM_dk[sequential_i][ind_j] * Dij;
432 _fa[sequential_i][j] = prefactor * (u_i - u_j);
433 _dfa[sequential_i][j][global_i] = prefactor;
434 _dfa[sequential_i][j][global_j] = -prefactor;
435 for (std::size_t ind_j = 0; ind_j < num_con_i; ++ind_j)
438 dprefactor_du[ind_j] * (u_i - u_j);
439 _dFij_dKik[sequential_i][j][ind_j] += dprefactor_dKij[ind_j] * (u_i - u_j);
441 _dFij_dKjk[sequential_i][j][index_j_to_i] += dprefactor_dKji * (u_i - u_j);
446 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
448 const std::vector<dof_id_type> & con_i =
450 const std::size_t num_con_i = con_i.size();
451 for (std::size_t j = 0; j < num_con_i; ++j)
453 const dof_id_type sequential_j = con_i[j];
454 if (sequential_i == sequential_j)
456 const unsigned index_j_to_i =
458 if (
_lij[sequential_j][index_j_to_i] <
_lij[sequential_i][j])
460 _fa[sequential_i][j] = -
_fa[sequential_j][index_j_to_i];
461 for (
const auto & dof_deriv :
_dfa[sequential_j][index_j_to_i])
462 _dfa[sequential_i][j][dof_deriv.first] = -dof_deriv.second;
463 for (std::size_t k = 0; k < num_con_i; ++k)
465 const std::size_t num_con_j =
467 for (std::size_t k = 0; k < num_con_j; ++k)
480 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
488 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
490 const std::vector<dof_id_type> & con_i =
492 const std::size_t num_con_i = con_i.size();
494 for (std::size_t j = 0; j < num_con_i; ++j)
496 const dof_id_type sequential_j = con_i[j];
497 const std::vector<dof_id_type> & con_j =
505 for (dof_id_type sequential_i = 0; sequential_i <
_number_of_nodes; ++sequential_i)
507 const std::vector<dof_id_type> & con_i =
509 const size_t num_con_i = con_i.size();
510 const dof_id_type index_i_to_i =
512 for (std::size_t j = 0; j < num_con_i; ++j)
514 const dof_id_type sequential_j = con_i[j];
516 const Real u_j =
_u_nodal[sequential_j];
519 _flux_out[sequential_i] -=
_lij[sequential_i][j] * u_j +
_fa[sequential_i][j];
522 for (
const auto & dof_deriv :
_dfa[sequential_i][j])
523 _dflux_out_du[sequential_i][dof_deriv.first] -= dof_deriv.second;
527 if (sequential_j == sequential_i)
528 for (dof_id_type k = 0; k < num_con_i; ++k)
532 for (dof_id_type k = 0; k < num_con_i; ++k)
535 if (sequential_j == sequential_i)
536 for (
unsigned k = 0; k < con_i.size(); ++k)
538 const unsigned index_k_to_i =
544 const unsigned index_j_to_i =
558 std::vector<Real> & dlimited_du,
559 std::vector<Real> & dlimited_dk)
const
562 dlimited_du.assign(num_con, 0.0);
563 dlimited_dk.assign(num_con, 0.0);
566 std::vector<Real> dp_du;
567 std::vector<Real> dp_dk;
572 std::vector<Real> dq_du;
573 std::vector<Real> dq_dk;
576 const Real r = q /
p;
581 const Real p2 = std::pow(
p, 2);
582 for (std::size_t j = 0; j < num_con; ++j)
584 const Real dr_du = dq_du[j] /
p - q * dp_du[j] / p2;
585 const Real dr_dk = dq_dk[j] /
p - q * dp_dk[j] / p2;
586 dlimited_du[j] = dlimited_dr * dr_du;
587 dlimited_dk[j] = dlimited_dr * dr_dk;
594 std::vector<Real> & dlimited_du,
595 std::vector<Real> & dlimited_dk)
const
598 dlimited_du.assign(num_con, 0.0);
599 dlimited_dk.assign(num_con, 0.0);
602 std::vector<Real> dp_du;
603 std::vector<Real> dp_dk;
608 std::vector<Real> dq_du;
609 std::vector<Real> dq_dk;
612 const Real r = q /
p;
617 const Real p2 = std::pow(
p, 2);
618 for (std::size_t j = 0; j < num_con; ++j)
620 const Real dr_du = dq_du[j] /
p - q * dp_du[j] / p2;
621 const Real dr_dk = dq_dk[j] /
p - q * dp_dk[j] / p2;
622 dlimited_du[j] = dlimited_dr * dr_du;
623 dlimited_dk[j] = dlimited_dr * dr_dk;
636 if ((
a >= 0.0 &&
b <= 0.0) || (a <= 0.0 && b >= 0.0))
638 const Real s = (
a > 0.0 ? 1.0 : -1.0);
640 const Real lal = std::abs(
a);
641 const Real lbl = std::abs(
b);
642 const Real dlbl = (
b >= 0.0 ? 1.0 : -1.0);
655 dlimited_db = s * dlbl;
661 limited = s * 2 * lal * lbl / (lal + lbl);
662 dlimited_db = s * 2 * lal * (dlbl / (lal + lbl) - lbl * dlbl / std::pow(lal + lbl, 2));
667 const Real av = 0.5 * std::abs(
a +
b);
668 if (2 * lal <= av && lal <= lbl)
671 limited = s * 2.0 * lal;
674 else if (2 * lbl <= av && lbl <= lal)
677 limited = s * 2.0 * lbl;
678 dlimited_db = s * 2.0 * dlbl;
687 dlimited_db = s * 0.5 * dlbl;
693 const Real term1 = std::min(2.0 * lal, lbl);
694 const Real term2 = std::min(lal, 2.0 * lbl);
697 if (2.0 * lal <= lbl)
699 limited = s * 2 * lal;
705 dlimited_db = s * dlbl;
710 if (lal <= 2.0 * lbl)
717 limited = s * 2.0 * lbl;
718 dlimited_db = s * 2.0 * dlbl;
728const std::map<dof_id_type, Real> &
734const std::vector<std::vector<Real>> &
754 dof_id_type node_i)
const
758 the_map[node_j] = 0.0;
764 std::vector<Real> & derivs,
765 std::vector<Real> & dpqdk)
const
768 const Real u_i =
_u_nodal[sequential_i];
771 const std::vector<dof_id_type> con_i =
773 const std::size_t num_con = con_i.size();
779 derivs.assign(num_con, 0.0);
780 dpqdk.assign(num_con, 0.0);
783 for (std::size_t j = 0; j < num_con; ++j)
785 const dof_id_type sequential_j = con_i[j];
786 if (sequential_j == sequential_i)
788 const Real kentry =
_kij[sequential_i][j];
791 const Real u_j =
_u_nodal[sequential_j];
792 const Real ujminusi = u_j - u_i;
795 switch (pq_plus_minus)
799 if (ujminusi < 0.0 && kentry < 0.0)
801 result += kentry * ujminusi;
803 derivs[i_index_i] -= kentry;
804 dpqdk[j] += ujminusi;
810 if (ujminusi > 0.0 && kentry < 0.0)
812 result += kentry * ujminusi;
814 derivs[i_index_i] -= kentry;
815 dpqdk[j] += ujminusi;
821 if (ujminusi > 0.0 && kentry > 0.0)
823 result += kentry * ujminusi;
825 derivs[i_index_i] -= kentry;
826 dpqdk[j] += ujminusi;
832 if (ujminusi < 0.0 && kentry > 0.0)
834 result += kentry * ujminusi;
836 derivs[i_index_i] -= kentry;
837 dpqdk[j] += ujminusi;
865 if (this->
hasBlocks(elem->subdomain_id()))
867 const processor_id_type elem_pid = elem->processor_id();
872 for (
unsigned i = 0; i < elem->n_nodes(); ++i)
882 auto nodes_action_functor = [
this](processor_id_type pid,
const std::vector<dof_id_type> & nts)
893 const processor_id_type pid = kv.first;
894 const std::size_t num_nodes = kv.second.size();
895 for (
unsigned i = 0; i < num_nodes; ++i)
900 const processor_id_type pid = kv.first;
901 const std::size_t num_nodes = kv.second.size();
902 for (
unsigned i = 0; i < num_nodes; ++i)
909 if (this->
hasBlocks(elem->subdomain_id()))
911 const processor_id_type elem_pid = elem->processor_id();
915 _pairs_to_receive[elem_pid] = std::vector<std::pair<dof_id_type, dof_id_type>>();
916 for (
unsigned i = 0; i < elem->n_nodes(); ++i)
917 for (
unsigned j = 0; j < elem->n_nodes(); ++j)
919 std::pair<dof_id_type, dof_id_type> the_pair(elem->node_id(i), elem->node_id(j));
929 auto pairs_action_functor =
930 [
this](processor_id_type pid,
const std::vector<std::pair<dof_id_type, dof_id_type>> & pts)
941 const processor_id_type pid = kv.first;
942 const std::size_t num_pairs = kv.second.size();
943 for (
unsigned i = 0; i < num_pairs; ++i)
952 const processor_id_type pid = kv.first;
953 const std::size_t num_pairs = kv.second.size();
954 for (
unsigned i = 0; i < num_pairs; ++i)
967 std::map<processor_id_type, std::vector<Real>> unodal_to_send;
970 const processor_id_type pid = kv.first;
971 unodal_to_send[pid] = std::vector<Real>();
972 for (
const auto & nd : kv.second)
973 unodal_to_send[pid].push_back(
_u_nodal[nd]);
976 auto unodal_action_functor =
977 [
this](processor_id_type pid,
const std::vector<Real> & unodal_received)
979 const std::size_t msg_size = unodal_received.size();
981 "Message size, " << msg_size
982 <<
", incompatible with nodes_to_receive, which has size "
984 for (
unsigned i = 0; i < msg_size; ++i)
987 Parallel::push_parallel_vector_data(this->
comm(), unodal_to_send, unodal_action_functor);
990 std::map<processor_id_type, std::vector<Real>> kij_to_send;
993 const processor_id_type pid = kv.first;
994 kij_to_send[pid] = std::vector<Real>();
995 for (
const auto & pr : kv.second)
996 kij_to_send[pid].push_back(
_kij[pr.first][pr.second]);
999 auto kij_action_functor = [
this](processor_id_type pid,
const std::vector<Real> & kij_received)
1001 const std::size_t msg_size = kij_received.size();
1003 "Message size, " << msg_size
1004 <<
", incompatible with pairs_to_receive, which has size "
1006 for (
unsigned i = 0; i < msg_size; ++i)
1009 Parallel::push_parallel_vector_data(this->
comm(), kij_to_send, kij_action_functor);
const ExecFlagType EXEC_LINEAR
Base class to compute Advective fluxes.
PQPlusMinusEnum
Signals to the PQPlusMinus method what should be computed.
std::vector< std::vector< Real > > _drM
drM[i][j] = d(rM[i])/d(u[j]). Here j indexes the j^th node connected to i
std::vector< std::vector< Real > > _fa
fa[sequential_i][j] sequential_j is the j^th connection to sequential_i
FluxLimiterTypeEnum
Determines Flux Limiter type (Page 135 of Kuzmin and Turek) "None" means that limitFlux=0 always,...
virtual void meshChanged() override
AdvectiveFluxCalculatorBase(const InputParameters ¶meters)
Real rPlus(dof_id_type sequential_i, std::vector< Real > &dlimited_du, std::vector< Real > &dlimited_dk) const
Returns the value of R_{i}^{+}, Eqn (49) of KT.
std::vector< Real > _u_nodal
_u_nodal[i] = value of _u at sequential node number i
std::vector< std::vector< Real > > _dDij_dKji
dDij_dKji[i][j] = d(D[i][j])/d(K[j][i]) for i!=j
std::vector< std::vector< Real > > _kij
Kuzmin-Turek K_ij matrix.
virtual void executeOnElement(dof_id_type global_i, dof_id_type global_j, unsigned local_i, unsigned local_j, unsigned qp)
This is called by multiple times in execute() in a double loop over _current_elem's nodes (local_i an...
std::vector< std::vector< std::vector< Real > > > _dFij_dKik
dFij_dKik[sequential_i][j][k] = d(fa[sequential_i][j])/d(K[sequential_i][k]).
std::vector< std::vector< Real > > _lij
virtual void buildCommLists()
When using multiple processors, other processors will compute:
std::map< processor_id_type, std::vector< std::pair< dof_id_type, dof_id_type > > > _pairs_to_send
_pairs_to_send[proc_id] indicates the k(i, j) pairs that we will send to proc_id _pairs_to_send is fi...
std::vector< std::vector< Real > > _dDii_dKij
dDii_dKij[i][j] = d(D[i][i])/d(K[i][j])
virtual void threadJoin(const UserObject &uo) override
PorousFlowConnectedNodes _connections
Holds the sequential and global nodal IDs, and info regarding mesh connections between them.
std::map< processor_id_type, std::vector< dof_id_type > > _nodes_to_receive
_nodes_to_receive[proc_id] = list of sequential nodal IDs.
virtual void timestepSetup() override
std::vector< std::vector< Real > > _dij
Vectors used in finalize()
virtual Real computeVelocity(unsigned i, unsigned j, unsigned qp) const =0
Computes the transfer velocity between current node i and current node j at the current qp in the cur...
void zeroedConnection(std::map< dof_id_type, Real > &the_map, dof_id_type node_i) const
Clears the_map, then, using _kij, constructs the_map so that the_map[node_id] = 0....
std::vector< std::map< dof_id_type, Real > > _dflux_out_du
_dflux_out_du[i][j] = d(flux_out[i])/d(u[j]).
std::vector< std::vector< Real > > _drP_dk
drP_dk[i][j] = d(rP[i])/d(K[i][j]). Here j indexes the j^th node connected to i
std::vector< std::vector< std::vector< Real > > > _dflux_out_dKjk
_dflux_out_dKjk[sequential_i][j][k] = d(flux_out[sequential_i])/d(K[j][k]).
Real rMinus(dof_id_type sequential_i, std::vector< Real > &dlimited_du, std::vector< Real > &dlimited_dk) const
Returns the value of R_{i}^{-}, Eqn (49) of KT.
Real getFluxOut(dof_id_type node_i) const
Returns the flux out of lobal node id.
std::vector< std::vector< Real > > _drM_dk
drM_dk[i][j] = d(rM[i])/d(K[i][j]). Here j indexes the j^th node connected to i
std::map< processor_id_type, std::vector< std::pair< dof_id_type, dof_id_type > > > _pairs_to_receive
_pairs_to_receive[proc_id] indicates the k(i, j) pairs that will be sent to us from proc_id _pairs_to...
std::vector< std::vector< Real > > _dDii_dKji
dDii_dKji[i][j] = d(D[i][i])/d(K[j][i])
virtual void finalize() override
virtual Real computeU(unsigned i) const =0
Computes the value of u at the local node id of the current element (_current_elem)
static InputParameters validParams()
std::vector< std::vector< std::vector< Real > > > _dFij_dKjk
dFij_dKjk[sequential_i][j][k] = d(fa[sequential_i][j])/d(K[sequential_j][k]).
enum AdvectiveFluxCalculatorBase::FluxLimiterTypeEnum _flux_limiter_type
std::vector< bool > _u_nodal_computed_by_thread
_u_nodal_computed_by_thread(i) = true if _u_nodal[i] has been computed in execute() by the thread on ...
const std::map< dof_id_type, Real > & getdFluxOutdu(dof_id_type node_i) const
Returns r where r[j] = d(flux out of global node i)/du(global node j) used in Jacobian computations.
std::vector< std::vector< Real > > _dDij_dKij
dDij_dKij[i][j] = d(D[i][j])/d(K[i][j]) for i!=j
std::vector< unsigned > _valence
_valence[i] = number of times, in a loop over elements seen by this processor (viz,...
processor_id_type _my_pid
processor ID of this object
std::size_t _number_of_nodes
Number of nodes held by the _connections object.
const Real _allowable_MB_wastage
A mooseWarning is issued if mb_wasted = (_connections.sizeSequential() - _connections....
virtual void execute() override
virtual void initialize() override
std::map< processor_id_type, std::vector< dof_id_type > > _nodes_to_send
_nodes_to_send[proc_id] = list of sequential nodal IDs.
Real PQPlusMinus(dof_id_type sequential_i, const PQPlusMinusEnum pq_plus_minus, std::vector< Real > &derivs, std::vector< Real > &dpq_dk) const
Returns the value of P_{i}^{+}, P_{i}^{-}, Q_{i}^{+} or Q_{i}^{-} (depending on pq_plus_minus) which ...
const std::vector< std::vector< Real > > & getdFluxOutdKjk(dof_id_type node_i) const
Returns r where r[j][k] = d(flux out of global node i)/dK[connected node j][connected node k] used in...
virtual void exchangeGhostedInfo()
Sends and receives multi-processor information regarding u_nodal and k_ij.
void limitFlux(Real a, Real b, Real &limited, Real &dlimited_db) const
flux limiter, L, on Page 135 of Kuzmin and Turek
bool _resizing_needed
whether _kij, etc, need to be sized appropriately (and valence recomputed) at the start of the timest...
std::vector< std::vector< Real > > _drP
drP[i][j] = d(rP[i])/d(u[j]). Here j indexes the j^th node connected to i
std::vector< std::vector< std::map< dof_id_type, Real > > > _dfa
dfa[sequential_i][j][global_k] = d(fa[sequential_i][j])/du[global_k].
unsigned getValence(dof_id_type node_i) const
Returns the valence of the global node i Valence is the number of times the node is encountered in a ...
std::vector< Real > _flux_out
_flux_out[i] = flux of "heat" from sequential node i
bool hasBlocks(const SubdomainName &name) const
static InputParameters validParams()
const QBase *const & _qrule
const Elem *const & _current_elem
const MooseArray< Real > & _coord
const MooseArray< Real > & _JxW
const libMesh::ConstElemRange & getNonlinearEvaluableElementRange()
virtual void meshChanged()
const std::string & name() const
void paramError(const std::string ¶m, Args... args) const
void mooseWarning(Args &&... args) const
bool isValueSet(const std::string &value) const
void finalizeAddingConnections()
Signal that all global node IDs have been added to the internal data structures.
const std::vector< dof_id_type > & sequentialConnectionsToSequentialID(dof_id_type sequential_node_ID) const
Return all the nodes (sequential node IDs) connected to the given sequential node ID All elements of ...
void addConnection(dof_id_type global_node_from, dof_id_type global_node_to)
Specifies that global_node_to is connected to global_node_from.
dof_id_type globalID(dof_id_type sequential_node_ID) const
Return the global node ID (node number in the mesh) corresponding to the provided sequential node ID.
std::size_t numNodes() const
number of nodes known by this class
unsigned indexOfSequentialConnection(dof_id_type sequential_node_ID_from, dof_id_type sequential_node_ID_to) const
Return the index of sequential_node_ID_to in the sequentialConnectionsToSequentialID(sequential_node_...
const std::vector< dof_id_type > & globalConnectionsToSequentialID(dof_id_type sequential_node_ID) const
Return all the nodes (global node IDs) connected to the given sequential node ID.
void finalizeAddingGlobalNodes()
Signal that all global node IDs have been added to the internal data structures.
void clear()
clear all data in readiness for adding global nodes and connections
void addGlobalNode(dof_id_type global_node_ID)
Add the given global_node_ID to the internal data structures If the global node ID has already been a...
unsigned indexOfGlobalConnection(dof_id_type global_node_ID_from, dof_id_type global_node_ID_to) const
Return the index of global_node_ID_to in the globalConnectionsToGlobalID(global_node_ID_from) vector.
std::size_t sizeSequential() const
Return the size of _sequential_id, for checking memory efficiency.
dof_id_type sequentialID(dof_id_type global_node_ID) const
Return the sequential node ID corresponding to the global node ID This is guaranteed to lie in the ra...
const std::vector< dof_id_type > & globalConnectionsToGlobalID(dof_id_type global_node_ID) const
Return all the nodes (global node IDs) connected to the given global node ID.
const ExecFlagEnum & _execute_enum
FEProblemBase & _fe_problem
const Parallel::Communicator & comm() const
processor_id_type n_processors() const
std::string stringify(const T &t)