https://mooseframework.inl.gov
Loading...
Searching...
No Matches
MeshAlignmentOneToMany.C
Go to the documentation of this file.
1//* This file is part of the MOOSE framework
2//* https://mooseframework.inl.gov
3//*
4//* All rights reserved, see COPYRIGHT for full restrictions
5//* https://github.com/idaholab/moose/blob/master/COPYRIGHT
6//*
7//* Licensed under LGPL 2.1, please see LICENSE for details
8//* https://www.gnu.org/licenses/lgpl-2.1.html
9
11#include "KDTree.h"
12#include "MooseUtils.h"
13
15 : MeshAlignmentBase(mesh), _max_coupling_size(0)
16{
17}
18
19void
21{
22 // Build the element mapping
23 if (_primary_elem_points.size() > 0 && _secondary_elem_points.size() > 0)
24 {
25 // find the primary elements that are nearest to the secondary elements
27 for (std::size_t i_secondary = 0; i_secondary < _secondary_elem_points.size(); i_secondary++)
28 {
29 unsigned int patch_size = 1;
30 std::vector<std::size_t> return_index(patch_size);
31 kd_tree.neighborSearch(_secondary_elem_points[i_secondary], patch_size, return_index);
32 const std::size_t i_primary = return_index[0];
33
34 const auto primary_elem_id = _primary_elem_ids[i_primary];
35 const auto secondary_elem_id = _secondary_elem_ids[i_secondary];
36
37 _secondary_elem_id_to_primary_elem_id[secondary_elem_id] = primary_elem_id;
38
39 auto it = _primary_elem_id_to_secondary_elem_ids.find(primary_elem_id);
41 _primary_elem_id_to_secondary_elem_ids.insert({primary_elem_id, {secondary_elem_id}});
42 else
43 it->second.push_back(secondary_elem_id);
44 }
45
46 // Determine max coupling size
47 for (const auto primary_elem_id : _primary_elem_ids)
48 if (hasCoupledSecondaryElemIDs(primary_elem_id))
49 {
50 const auto & secondary_elem_ids = getCoupledSecondaryElemIDs(primary_elem_id);
51 _max_coupling_size = std::max(secondary_elem_ids.size(), _max_coupling_size);
52 }
53 }
54}
55
56void
58 const RealVectorValue & axis_direction)
59{
60 if (_primary_elem_points.size() > 0 && _secondary_elem_points.size() > 0)
61 {
62 // Check if meshes are aligned: all secondary boundary faces paired to a
63 // primary element/face must have the same axial coordinate.
65 for (const auto i_primary : index_range(_primary_elem_ids))
66 {
67 const auto primary_elem_id = _primary_elem_ids[i_primary];
68 const auto primary_elem_point = _primary_elem_points[i_primary];
69 const auto primary_ax_coord = axis_direction * (primary_elem_point - axis_point);
70
71 if (hasCoupledSecondaryElemIDs(primary_elem_id))
72 {
73 const auto & secondary_elem_ids = getCoupledSecondaryElemIDs(primary_elem_id);
74 for (const auto secondary_elem_id : secondary_elem_ids)
75 {
76 auto it =
77 std::find(_secondary_elem_ids.begin(), _secondary_elem_ids.end(), secondary_elem_id);
78 const auto i_secondary = std::distance(_secondary_elem_ids.begin(), it);
79 const auto secondary_elem_point = _secondary_elem_points[i_secondary];
80 const auto secondary_ax_coord = axis_direction * (secondary_elem_point - axis_point);
81 if (!MooseUtils::absoluteFuzzyEqual(secondary_ax_coord, primary_ax_coord))
82 _meshes_are_aligned = false;
83 }
84 }
85 else
86 _meshes_are_aligned = false;
87 }
88 }
89}
90
91bool
92MeshAlignmentOneToMany::hasCoupledPrimaryElemID(const dof_id_type & secondary_elem_id) const
93{
94 return _secondary_elem_id_to_primary_elem_id.find(secondary_elem_id) !=
96}
97
98dof_id_type
99MeshAlignmentOneToMany::getCoupledPrimaryElemID(const dof_id_type & secondary_elem_id) const
100{
101 mooseAssert(hasCoupledPrimaryElemID(secondary_elem_id),
102 "The element ID has no coupled elements.");
103 return _secondary_elem_id_to_primary_elem_id.find(secondary_elem_id)->second;
104}
105
106bool
107MeshAlignmentOneToMany::hasCoupledSecondaryElemIDs(const dof_id_type & primary_elem_id) const
108{
109 return _primary_elem_id_to_secondary_elem_ids.find(primary_elem_id) !=
111}
112
113const std::vector<dof_id_type> &
114MeshAlignmentOneToMany::getCoupledSecondaryElemIDs(const dof_id_type & primary_elem_id) const
115{
116 mooseAssert(hasCoupledSecondaryElemIDs(primary_elem_id),
117 "The element ID has no coupled elements.");
118 return _primary_elem_id_to_secondary_elem_ids.find(primary_elem_id)->second;
119}
120
121unsigned int
122MeshAlignmentOneToMany::getCoupledPrimaryElemQpIndex(const dof_id_type & secondary_elem_id,
123 const unsigned int & secondary_qp) const
124{
125 auto it = _secondary_elem_id_to_qp_indices.find(secondary_elem_id);
126 mooseAssert(it != _secondary_elem_id_to_qp_indices.end(),
127 "The element ID has no coupled quadrature point indices.");
128 mooseAssert(secondary_qp < it->second.size(), "The quadrature index does not exist in the map.");
129 return it->second[secondary_qp];
130}
void neighborSearch(const Point &query_point, unsigned int patch_size, std::vector< std::size_t > &return_index)
Builds mapping between two aligned subdomains/boundaries.
bool _meshes_are_aligned
Flag that meshes are aligned.
const MooseMesh & _mesh
Mesh.
std::vector< dof_id_type > _primary_elem_ids
List of primary element IDs.
std::vector< Point > _primary_elem_points
List of primary element points.
std::vector< Point > _secondary_elem_points
List of secondary element points.
std::vector< dof_id_type > _secondary_elem_ids
List of secondary element IDs.
void checkAlignment(const Point &axis_point, const RealVectorValue &axis_direction)
Checks the alignment and sets _mesh_alignment accordingly.
void buildMapping()
Builds the mapping using the extracted mesh information.
unsigned int getCoupledPrimaryElemQpIndex(const dof_id_type &secondary_elem_id, const unsigned int &secondary_qp) const
Gets the quadrature point index on the primary element corresponding to the quadrature point index on...
bool hasCoupledSecondaryElemIDs(const dof_id_type &primary_elem_id) const
Returns true if the given primary element ID has coupled secondary elements.
std::map< dof_id_type, std::vector< unsigned int > > _secondary_elem_id_to_qp_indices
Map of secondary element ID to vector of coupled quadrature points.
std::map< dof_id_type, std::vector< dof_id_type > > _primary_elem_id_to_secondary_elem_ids
Map of primary element ID to coupled secondary element IDs.
dof_id_type getCoupledPrimaryElemID(const dof_id_type &secondary_elem_id) const
Gets the coupled primary element ID for a given secondary element ID.
unsigned long _max_coupling_size
The maximum number of secondary elements coupled to any primary element.
MeshAlignmentOneToMany(const MooseMesh &mesh)
Constructor.
const std::vector< dof_id_type > & getCoupledSecondaryElemIDs(const dof_id_type &primary_elem_id) const
Gets the coupled secondary element IDs for a given primary element ID.
std::map< dof_id_type, dof_id_type > _secondary_elem_id_to_primary_elem_id
Map of secondary element ID to coupled primary element ID.
bool hasCoupledPrimaryElemID(const dof_id_type &secondary_elem_id) const
Returns true if the given secondary element ID has a coupled primary element.
unsigned int getMaxLeafSize() const
MeshBase & mesh