32 "Transfers functor data at the MultiApp position by evaluating the functor inside its domain " 33 "of definition and extrapolating with a user-selected behavior outside");
38 params.
suppressParameter<std::vector<unsigned int>>(
"source_variable_components");
41 "source_functors",
"Functors providing the values to transfer to the target variables");
50 MooseEnum extrapolation(
"flat evaluate_oob nearest-node nearest-elem",
"nearest-node");
53 "How to extrapolate the functors when a target point for the transfer " 54 "is outside the domain of evaluation");
57 params.
renameParam(
"use_nearest_app",
"assume_nearest_app_holds_evaluation_location",
"");
66 _functor_names(getParam<
std::vector<MooseFunctorName>>(
"source_functors")),
67 _extrapolation_behavior(getParam<
MooseEnum>(
"extrapolation_behavior"))
72 "Flat (single-constant) extrapolation must be selected if an extrapolation constant " 76 "Flat (single-constant) extrapolation must be selected if an extrapolation post-" 77 "treatment is specified");
81 paramError(
"source_functors",
"Should be the same size as target 'variable'");
153 unsigned int max_leaf_size = 0;
160 for (
const auto app_i :
make_range(num_apps_per_tree))
174 const auto & functor =
_functors[i_from][var_index];
180 std::set<SubdomainID> from_blocks;
184 if (functor->hasBlocks(bl))
185 from_blocks.insert(bl);
193 for (
const auto & node : from_mesh.getMesh().local_node_ptr_range())
198 bool on_at_least_one_block =
false;
199 bool on_boundary =
false;
200 for (
const auto eid : libmesh_map_find(node_to_elem_map, node->id()))
202 bool has_block = functor->hasBlocks(from_mesh.elemPtr(eid)->subdomain_id());
204 on_at_least_one_block =
true;
208 const auto elem = from_mesh.elemPtr(eid);
209 for (
const auto side : elem->side_index_range())
210 if (!elem->neighbor_ptr(side) &&
211 elem->is_node_on_side(elem->get_node_index(node), side))
216 if (!on_at_least_one_block || !on_boundary)
239 MeshDivisionTransferUse::MATCH_DIVISION_INDEX ||
242 MeshDivisionTransferUse::MATCH_SUBAPP_INDEX) &&
243 tree_division_index != node_div_index)
265 _local_values[i_source].push_back((*functor)(node_arg, time_arg));
272 for (
const auto & elem : from_mesh.getMesh().local_element_ptr_range())
275 if (!functor->hasBlocks(elem->subdomain_id()))
279 bool at_a_boundary =
false;
280 for (
const auto side : elem->side_index_range())
283 if (!elem->neighbor_ptr(side))
285 at_a_boundary =
true;
289 else if (!functor->hasBlocks(elem->neighbor_ptr(side)->subdomain_id()))
291 at_a_boundary =
true;
311 const auto node_div_index =
320 MeshDivisionTransferUse::MATCH_DIVISION_INDEX ||
323 MeshDivisionTransferUse::MATCH_SUBAPP_INDEX) &&
324 tree_division_index != node_div_index)
329 const auto transformed_centroid =
347 _local_values[i_source].push_back((*functor)(elem_arg, time_arg));
350 max_leaf_size =
std::max(max_leaf_size, from_mesh.getMaxLeafSize());
354 std::shared_ptr<KDTree> _kd_tree =
355 std::make_shared<KDTree>(
_local_points[i_source], max_leaf_size);
362 const unsigned int var_index,
363 const std::vector<std::pair<Point, unsigned int>> & incoming_points,
364 std::vector<std::pair<Real, Real>> & outgoing_vals)
371 const unsigned int var_index,
372 const std::vector<std::pair<Point, unsigned int>> & incoming_points,
373 std::vector<std::pair<Real, Real>> & outgoing_vals)
376 std::set<const Elem *> elem_candidates;
379 for (
const auto & [pt, mesh_div] : incoming_points)
383 bool point_found =
false;
397 for (
const auto app_i :
make_range(num_apps_per_tree))
399 const auto app_index =
getAppIndex(i_source, app_i);
402 const Point app_local_pt =
406 const auto & functor = *
_functors[app_index][var_index];
409 std::set<SubdomainID> from_blocks;
413 :
_from_problems[app_index]->mesh().getMesh().get_mesh_subdomains())
414 if (functor.hasBlocks(bl))
415 from_blocks.insert(bl);
420 elem_candidates.clear();
421 if (from_blocks.size())
422 (*
_point_locators[app_index])(app_local_pt, elem_candidates, &from_blocks);
425 if (elem_candidates.size())
440 unsigned int num_values = 0;
441 for (
const auto elem : elem_candidates)
447 elem->processor_id() !=
_from_problems[app_index]->processor_id())
454 value += functor(elem_pt_arg, time_arg);
462 outgoing_vals[i_pt] = {
value, 0};
495 const Point oob_local_pt =
497 const auto & functor = *
_functors[first_app][var_index];
505 for (
const auto index : return_index)
508 const auto new_distance = dist_sum / return_dist_sqr.size();
509 if (new_distance < outgoing_vals[i_pt].second)
513 outgoing_vals[i_pt] = {functor(elem_pt_arg, time_arg), new_distance};
An interface for accessing Moose::Functors for systems that do not care about automatic differentiati...
void execute() override
Execute the transfer.
const MooseEnum _post_transfer_extrapolation
How to post treat after the transfer.
const ExecFlagType EXEC_TRANSFER
void initialSetup() override
Method called at the beginning of the simulation for checking integrity or doing one-time setup...
unsigned int getNumDivisions() const
Number of divisions (nearest-positions or source mesh divisions) used when building KD-Trees...
const bool _group_subapps
Whether to group data when creating the nearest-point regions.
static const std::set< SubdomainID > undefined_subdomain_connection
A static member that can be used when the connection of a node to subdomains is unknown.
Base class for working with KDTrees in transfers, whether for interpolation or extrapolation.
void computeNumSources()
Pre-compute the number of sources Number of KDTrees used to hold the locations and variable value dat...
void paramError(const std::string ¶m, Args... args) const
Emits an error prefixed with the file and line number of the given param (from the input file) along ...
MooseEnum _current_direction
Point getPointInSourceAppFrame(const Point &p, unsigned int local_i_from, const std::string &phase) const
Get the source app point from a point in the reference frame.
MultiAppGeneralFieldFunctorTransfer(const InputParameters ¶meters)
const std::map< dof_id_type, std::vector< dof_id_type > > & nodeToActiveSemilocalElemMap()
If not already created, creates a map from every node to all active semilocal elements to which they ...
void registerConflict(unsigned int problem, dof_id_type dof_id, Point p, Real dist, bool local)
Register a potential value conflict, e.g.
static constexpr Real TOLERANCE
virtual void evaluateInterpValues(const unsigned int var_index, const std::vector< std::pair< Point, unsigned int >> &incoming_points, std::vector< std::pair< Real, Real >> &outgoing_vals) override
Transfers a functor (can be variable, function, functor material property, spatial UO...
unsigned int getAppIndex(unsigned int kdtree_index, unsigned int app_index_in_tree) const
Get the index of the app when inside of a KD-Tree source loop, where multiple applications could be l...
virtual void execute() override
Execute the transfer.
void checkParentAppUserObjectExecuteOn(const std::string &object_name) const
Checks the execute_on flags for user object transfers with user objects on the source app which is al...
bool inBlocks(const std::set< SubdomainID > &blocks, const MooseMesh &mesh, const Elem *elem) const override
FEProblemBase & _fe_problem
static InputParameters validParams()
std::vector< const MeshDivision * > _from_mesh_divisions
Division of the origin mesh.
bool hasUserObject(const std::string &name) const
Check if there if a user object of given name.
A structure that is used to evaluate Moose functors at an arbitrary physical point contained within a...
The following methods are specializations for using the libMesh::Parallel::packed_range_* routines fo...
bool closestToPosition(unsigned int pos_index, const Point &pt) const
Whether a point is closest to a position at the index specified than any other position.
unsigned int _num_sources
Number of KD-Trees to create.
Specialization of SubProblem for solving nonlinear equations plus auxiliary equations.
std::set< BoundaryID > _from_boundaries
Origin boundary(ies) restriction.
auto max(const L &left, const R &right)
const Positions * _nearest_positions_obj
void evaluateNearestNodeFromKDTrees(const Point &pt, unsigned int source_index, std::pair< Real, Real > &outgoing_val, bool &point_found)
Search all local KD-trees for the nearest node/element and update outgoing_val.
unsigned int getNumAppsPerTree() const
Number of applications which contributed nearest-locations to each KD-tree.
void buildKDTrees(const unsigned int var_index) override
virtual void prepareEvaluationOfInterpValues(const unsigned int var_index) override
const std::string & name() const
Get the name of the class.
const std::vector< MooseFunctorName > _functor_names
Names of the source functors.
void errorIfObjectExecutesOnTransferInSourceApp(const std::string &object_name) const
Error if executing this MooseObject on EXEC_TRANSFER in a source multiapp (from_multiapp, e.g.
Real value(unsigned n, unsigned alpha, unsigned beta, Real x)
void initialSetup() override
Method called at the beginning of the simulation for checking integrity or doing one-time setup...
const std::vector< AuxVariableName > _to_var_names
Name of variables transferring to.
bool _search_value_conflicts
Whether to look for conflicts between origin points, multiple valid values for a target point...
This is a "smart" enum class intended to replace many of the shortcomings in the C++ enum type It sho...
A structure that is used to evaluate Moose functors logically at an element/cell center.
unsigned int getGlobalSourceAppIndex(unsigned int i_from) const
Return the global app index from the local index in the "from-multiapp" transfer direction.
std::vector< std::unique_ptr< libMesh::PointLocatorBase > > _point_locators
unsigned int INVALID_DIVISION_INDEX
Invalid subdomain id to return when outside the mesh division.
const MooseEnum _extrapolation_behavior
How to determine values where the target mesh does not overlap the source mesh.
static InputParameters validParams()
std::vector< std::vector< const Moose::Functor< Real > * > > _functors
Pointers to the source functors.
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
const MooseEnum & _to_mesh_division_behavior
How to use the target mesh divisions to restrict the transfer.
std::vector< std::unique_ptr< MultiAppCoordTransform > > _from_transforms
IntRange< T > make_range(T beg, T end)
virtual MooseMesh & mesh() override
bool _displaced_source_mesh
True if displaced mesh is used for the source mesh, otherwise false.
std::set< SubdomainID > _from_blocks
Origin block(s) restriction.
State argument for evaluating functors.
bool checkRestrictionsForSource(const Point &pt, const unsigned int valid_mesh_div, const unsigned int i_from) const
Examine all spatial restrictions that could preclude this source from being a valid source for this p...
static InputParameters validParams()
registerMooseObject("MooseApp", MultiAppGeneralFieldFunctorTransfer)
virtual void prepareEvaluationOfInterpValues(const unsigned int var_index) override
unsigned int _num_nearest_points
Number of points to consider.
virtual void computeUserObjectByName(const ExecFlagType &type, const Moose::AuxGroup &group, const std::string &name)
Compute an user object with the given name.
void evaluateValues(const unsigned int var_index, const std::vector< std::pair< Point, unsigned int >> &incoming_points, std::vector< std::pair< Real, Real >> &outgoing_vals)
std::vector< bool > _functor_is_variable
Whether the functor is a variable.
std::vector< std::vector< Real > > _local_values
Values of the variable being transferred at all the points in _local_points.
bool isParamSetByUser(const std::string &name) const
Test if the supplied parameter is set by a user, as opposed to not set or set to default.
bool onBoundaries(const std::set< BoundaryID > &boundaries, const MooseMesh &mesh, const Node *node) const
std::vector< std::vector< Point > > _local_points
All the nodes that meet the spatial restrictions in all the local source apps.
std::vector< FEProblemBase * > _from_problems
auto index_range(const T &sizable)
std::vector< std::shared_ptr< KDTree > > _local_kdtrees
KD-Trees for all the local source apps.
const MooseEnum & _from_mesh_division_behavior
How to use the origin mesh divisions to restrict the transfer.
const bool _use_nearest_app
Whether to keep track of the distance from the requested point to the app position.