https://mooseframework.inl.gov
Loading...
Searching...
No Matches
Public Types | Public Member Functions | Static Public Member Functions | Public Attributes | Static Public Attributes | Protected Member Functions | Static Protected Member Functions | Protected Attributes | Private Member Functions | Static Private Member Functions | Private Attributes | List of all members
SCMTriAssemblyMeshGenerator Class Reference

Mesh generator that builds a mesh of 1D lines representing subchannels and pins in a triangular assembly. More...

#include <SCMTriAssemblyMeshGenerator.h>

Inheritance diagram for SCMTriAssemblyMeshGenerator:
[legend]

Public Types

typedef DataFileName DataFileParameterType
 

Public Member Functions

 SCMTriAssemblyMeshGenerator (const InputParameters &parameters)
 
std::unique_ptr< MeshBase > generate () override
 
std::unique_ptr< CSG::CSGBasegenerateInternalCSG ()
 
std::unique_ptr< MeshBase > generateInternal ()
 
const std::set< MeshGeneratorName > & getRequestedMeshGenerators () const
 
const std::set< MeshGeneratorName > & getRequestedMeshGeneratorsForSub () const
 
void addParentMeshGenerator (const MeshGenerator &mg, const AddParentChildKey)
 
void addChildMeshGenerator (const MeshGenerator &mg, const AddParentChildKey)
 
const std::set< const MeshGenerator *, Comparator > & getParentMeshGenerators () const
 
const std::set< const MeshGenerator *, Comparator > & getChildMeshGenerators () const
 
const std::set< const MeshGenerator *, Comparator > & getSubMeshGenerators () const
 
bool isParentMeshGenerator (const MeshGeneratorName &name, const bool direct=true) const
 
bool isChildMeshGenerator (const MeshGeneratorName &name, const bool direct=true) const
 
bool isNullMeshName (const MeshGeneratorName &name) const
 
bool hasSaveMesh () const
 
bool hasOutput () const
 
const std::string & getSavedMeshName () const
 
bool hasGenerateData () const
 
bool hasGenerateCSG () const
 
bool isDataOnly () const
 
virtual bool enabled () const
 
std::shared_ptr< MooseObjectgetSharedPtr ()
 
std::shared_ptr< const MooseObjectgetSharedPtr () const
 
bool isKokkosObject () const
 
MooseAppgetMooseApp () const
 
const std::string & type () const
 
const std::string & name () const
 
std::string typeAndName () const
 
MooseObjectParameterName uniqueParameterName (const std::string &parameter_name) const
 
MooseObjectName uniqueName () const
 
const InputParametersparameters () const
 
const hit::Node * getHitNode () const
 
bool hasBase () const
 
const std::string & getBase () const
 
const TgetParam (const std::string &name) const
 
std::vector< std::pair< T1, T2 > > getParam (const std::string &param1, const std::string &param2) const
 
const TqueryParam (const std::string &name) const
 
const TgetRenamedParam (const std::string &old_name, const std::string &new_name) const
 
T getCheckedPointerParam (const std::string &name, const std::string &error_string="") const
 
bool isParamValid (const std::string &name) const
 
bool isParamSetByUser (const std::string &name) const
 
void connectControllableParams (const std::string &parameter, const std::string &object_type, const std::string &object_name, const std::string &object_parameter) const
 
void paramError (const std::string &param, Args... args) const
 
void paramWarning (const std::string &param, Args... args) const
 
void paramWarning (const std::string &param, Args... args) const
 
void paramInfo (const std::string &param, Args... args) const
 
std::string messagePrefix (const bool hit_prefix=true) const
 
std::string errorPrefix (const std::string &) const
 
void mooseError (Args &&... args) const
 
void mooseDocumentedError (const std::string &repo_name, const unsigned int issue_num, Args &&... args) const
 
void mooseErrorNonPrefixed (Args &&... args) const
 
void mooseWarning (Args &&... args) const
 
void mooseWarning (Args &&... args) const
 
void mooseWarningNonPrefixed (Args &&... args) const
 
void mooseWarningNonPrefixed (Args &&... args) const
 
void mooseDeprecated (Args &&... args) const
 
void mooseDeprecated (Args &&... args) const
 
void mooseDeprecatedNoTrace (Args &&... args) const
 
void mooseInfo (Args &&... args) const
 
void callMooseError (std::string msg, const bool with_prefix, const hit::Node *node=nullptr, const bool show_trace=true) const
 
std::string getDataFileName (const std::string &param) const
 
std::string getDataFileNameByName (const std::string &relative_path) const
 
std::string getDataFilePath (const std::string &relative_path) const
 
const Parallel::Communicator & comm () const
 
processor_id_type n_processors () const
 
processor_id_type processor_id () const
 

Static Public Member Functions

static InputParameters validParams ()
 
static bool hasGenerateData (const InputParameters &params)
 
static bool hasGenerateCSG (const InputParameters &params)
 
static void callMooseError (MooseApp *const app, const InputParameters &params, std::string msg, const bool with_prefix, const hit::Node *node, const bool show_trace=true)
 
static void setHasGenerateData (InputParameters &params)
 
static void setHasGenerateCSG (InputParameters &params)
 

Public Attributes

 usingCombinedWarningSolutionWarnings
 
const ConsoleStream _console
 

Static Public Attributes

static const std::string data_only_param
 
static const std::string type_param
 
static const std::string name_param
 
static const std::string unique_name_param
 
static const std::string app_param
 
static const std::string moose_base_param
 
static const std::string kokkos_object_param
 
static constexpr auto SYSTEM
 
static constexpr auto NAME
 

Protected Member Functions

void buildPinMesh (MeshBase &mesh_base)
 Build the 1D pin elements and append them to the subchannel mesh.
 
virtual void generateData ()
 
virtual std::unique_ptr< CSG::CSGBasegenerateCSG ()
 
TcopyMeshProperty (const std::string &target_data_name, const std::string &source_data_name, const std::string &source_mesh)
 
TcopyMeshProperty (const std::string &source_data_name, const std::string &source_mesh)
 
std::unique_ptr< MeshBase > & getMesh (const std::string &param_name, const bool allow_invalid=false)
 
std::vector< std::unique_ptr< MeshBase > * > getMeshes (const std::string &param_name)
 
std::unique_ptr< MeshBase > & getMeshByName (const MeshGeneratorName &mesh_generator_name)
 
std::vector< std::unique_ptr< MeshBase > * > getMeshesByName (const std::vector< MeshGeneratorName > &mesh_generator_names)
 
std::unique_ptr< CSG::CSGBase > & getCSGBase (const std::string &param_name)
 
std::unique_ptr< CSG::CSGBase > & getCSGBaseByName (const MeshGeneratorName &mesh_generator_name)
 
std::vector< std::unique_ptr< CSG::CSGBase > * > getCSGBases (const std::string &param_name)
 
std::vector< std::unique_ptr< CSG::CSGBase > * > getCSGBasesByName (const std::vector< MeshGeneratorName > &mesh_generator_names)
 
void declareMeshForSub (const std::string &param_name)
 
void declareMeshesForSub (const std::string &param_name)
 
void declareMeshForSubByName (const MeshGeneratorName &mesh_generator_name)
 
void declareMeshesForSubByName (const std::vector< MeshGeneratorName > &mesh_generator_names)
 
std::unique_ptr< MeshBase > buildMeshBaseObject (unsigned int dim=libMesh::invalid_uint)
 
std::unique_ptr< ReplicatedMesh > buildReplicatedMesh (unsigned int dim=libMesh::invalid_uint)
 
std::unique_ptr< DistributedMesh > buildDistributedMesh (unsigned int dim=libMesh::invalid_uint)
 
void addMeshSubgenerator (const std::string &type, const std::string &name, Ts... extra_input_parameters)
 
void addMeshSubgenerator (const std::string &type, const std::string &name, InputParameters params)
 
void declareNullMeshName (const MeshGeneratorName &name)
 
void flagInvalidSolutionInternal (const InvalidSolutionID invalid_solution_id) const
 
InvalidSolutionID registerInvalidSolutionInternal (const std::string &message, const bool warning) const
 
const TgetMeshProperty (const std::string &data_name, const std::string &prefix)
 
const TgetMeshProperty (const std::string &data_name)
 
bool hasMeshProperty (const std::string &data_name, const std::string &prefix) const
 
bool hasMeshProperty (const std::string &data_name, const std::string &prefix) const
 
bool hasMeshProperty (const std::string &data_name) const
 
bool hasMeshProperty (const std::string &data_name) const
 
std::string meshPropertyName (const std::string &data_name) const
 
TdeclareMeshProperty (const std::string &data_name, Args &&... args)
 
TdeclareMeshProperty (const std::string &data_name, const T &data_value)
 
TdeclareMeshProperty (const std::string &data_name, Args &&... args)
 
TdeclareMeshProperty (const std::string &data_name, const T &data_value)
 
TsetMeshProperty (const std::string &data_name, Args &&... args)
 
TsetMeshProperty (const std::string &data_name, const T &data_value)
 
TsetMeshProperty (const std::string &data_name, Args &&... args)
 
TsetMeshProperty (const std::string &data_name, const T &data_value)
 

Static Protected Member Functions

static std::string meshPropertyName (const std::string &data_name, const std::string &prefix)
 

Protected Attributes

const Real _unheated_length_entry
 unheated length of the fuel Pin at the entry of the assembly
 
const Real _heated_length
 heated length of the fuel Pin
 
const Real _unheated_length_exit
 unheated length of the fuel Pin at the exit of the assembly
 
const unsigned int _subchannel_block_id
 subchannel block index
 
const unsigned int _pin_block_id
 pin block index
 
std::vector< Real > _z_grid
 axial location of nodes
 
std::vector< std::vector< Real > > _k_grid
 axial form loss coefficient per computational cell
 
const std::vector< Real > & _spacer_z
 axial location of the spacers
 
const std::vector< Real > & _spacer_k
 form loss coefficient of the spacers
 
const std::vector< Real > _z_blockage
 axial location of blockage (inlet, outlet) [m]
 
const std::vector< unsigned int_index_blockage
 index of subchannels affected by blockage
 
const std::vector< Real > _reduction_blockage
 area reduction of subchannels affected by blockage
 
const std::vector< Real > _k_blockage
 form loss coefficient of subchannels affected by blockage
 
const Real _pitch
 Distance between the neighbor fuel pins, pitch.
 
const Real & _kij
 Lateral form loss coefficient.
 
const Real _pin_diameter
 fuel Pin diameter
 
const unsigned int _n_cells
 number of axial cells
 
const unsigned int _n_rings
 number of rings of fuel pins
 
unsigned int _n_channels
 number of subchannels
 
const Real _flat_to_flat
 the distance between flat surfaces of the duct facing each other
 
const Real _dwire
 wire diameter
 
const Real _hwire
 wire lead length
 
const Real _duct_to_pin_gap
 the gap thickness between the duct and peripheral fuel pins
 
std::vector< std::vector< Node * > > _nodes
 nodes
 
std::vector< std::vector< Node * > > _pin_nodes
 pin nodes
 
std::vector< std::pair< unsigned int, unsigned int > > _gap_to_chan_map
 stores the channel pairs for each gap
 
std::vector< std::pair< unsigned int, unsigned int > > _gap_to_pin_map
 stores the fuel pin pairs for each gap each gap
 
std::vector< std::vector< unsigned int > > _chan_to_gap_map
 stores the gaps that forms each subchannel
 
std::vector< std::vector< Real > > _sign_id_crossflow_map
 Defines the global cross-flow direction -1 or 1 for each subchannel and for all gaps that are belonging to the corresponding subchannel.
 
std::vector< std::vector< Real > > _gij_map
 gap size
 
std::vector< std::vector< Real > > _subchannel_position
 x,y coordinates of the subchannel centroids
 
std::vector< Point > _pin_position
 x,y coordinates of the fuel pins
 
std::vector< std::vector< Real > > _pins_in_rings
 fuel pins that are belonging to each ring
 
std::vector< std::vector< unsigned int > > _chan_to_pin_map
 stores the fuel pins belonging to each subchannel
 
std::vector< std::vector< unsigned int > > _pin_to_chan_map
 stores the map from pins to channels
 
unsigned int _npins
 number of fuel pins
 
unsigned int _n_gaps
 number of gaps
 
std::vector< EChannelType_subch_type
 subchannel type
 
std::vector< EChannelType_gap_type
 gap type
 
std::vector< std::pair< unsigned int, unsigned int > > _gap_pairs_sf
 sweeping flow model gap pairs per channel to specify directional edge flow
 
std::vector< std::pair< unsigned int, unsigned int > > _chan_pairs_sf
 sweeping flow model channel pairs to specify directional edge flow
 
MooseMesh *const _mesh
 
const bool & _enabled
 
MooseApp_app
 
Factory_factory
 
ActionFactory_action_factory
 
const std::string & _type
 
const std::string & _name
 
const InputParameters_pars
 
const Parallel::Communicator & _communicator
 

Private Member Functions

virtual std::string meshPropertyPrefix (const std::string &) const override final
 
void checkGetMesh (const MeshGeneratorName &mesh_generator_name, const std::string &param_name) const
 
const MeshGeneratorName * getMeshGeneratorNameFromParam (const std::string &param_name, const bool allow_invalid) const
 
const std::vector< MeshGeneratorName > & getMeshGeneratorNamesFromParam (const std::string &param_name) const
 
RestartableDataValuesetMeshPropertyHelper (const std::string &data_name)
 
const RestartableDataValuegetMeshPropertyInternal (const std::string &data_name, const std::string &prefix) const
 
void mooseErrorInternal (Args &&... args) const
 

Static Private Member Functions

static const hit::Node * getHitNode (const InputParameters &params)
 
static std::string messagePrefix (const InputParameters &params, const bool hit_prefix)
 

Private Attributes

std::set< MeshGeneratorName > _requested_mesh_generators
 
std::set< MeshGeneratorName > _requested_mesh_generators_for_sub
 
std::vector< std::pair< std::string, std::unique_ptr< MeshBase > * > > _requested_meshes
 
std::vector< std::pair< std::string, std::unique_ptr< CSG::CSGBase > * > > _requested_csg_bases
 
std::unique_ptr< MeshBase > _null_mesh
 
std::unique_ptr< CSG::CSGBase_null_csg_base
 
std::set< const MeshGenerator *, Comparator > _parent_mesh_generators
 
std::set< const MeshGenerator *, Comparator > _child_mesh_generators
 
std::set< const MeshGenerator *, Comparator > _sub_mesh_generators
 
std::set< std::string > _null_mesh_names
 
const std::string & _save_with_name
 
const bool _data_only
 
const ParallelParamObject_parent
 
const MooseBase_si_moose_base
 
const FEProblemBase_si_problem
 
MooseApp_meta_data_app
 
const MooseObject *const _meta_data_object
 

Detailed Description

Mesh generator that builds a mesh of 1D lines representing subchannels and pins in a triangular assembly.

Definition at line 19 of file SCMTriAssemblyMeshGenerator.h.

Constructor & Destructor Documentation

◆ SCMTriAssemblyMeshGenerator()

SCMTriAssemblyMeshGenerator::SCMTriAssemblyMeshGenerator ( const InputParameters parameters)

initial assignment

Build channel-gap connectivity from the channel-pin and gap-pin maps.

Center channels are bounded by three center gaps connecting their three pin pairs. Edge channels are bounded by one center gap between their two pins and two perimeter gaps along the duct. Corner channels are bounded by the two perimeter gaps that meet at the corner pin.

For a two-ring assembly every outer-ring pin is a corner pin. Consequently an edge channel can find a corner channel at both of its endpoint pins. The edge still owns only three local gap entries, matching _sign_id_crossflow_map and the reverse _gap_to_chan_map construction below, so the second corner lookup is skipped once those three entries are already present.

Definition at line 78 of file SCMTriAssemblyMeshGenerator.C.

79 : MeshGenerator(params),
80 _unheated_length_entry(getParam<Real>("unheated_length_entry")),
81 _heated_length(getParam<Real>("heated_length")),
82 _unheated_length_exit(getParam<Real>("unheated_length_exit")),
83 _subchannel_block_id(getParam<unsigned int>("subchannel_block_id")),
84 _pin_block_id(getParam<unsigned int>("pin_block_id")),
85 _spacer_z(getParam<std::vector<Real>>("spacer_z")),
86 _spacer_k(getParam<std::vector<Real>>("spacer_k")),
87 _z_blockage(getParam<std::vector<Real>>("z_blockage")),
88 _index_blockage(getParam<std::vector<unsigned int>>("index_blockage")),
89 _reduction_blockage(getParam<std::vector<Real>>("reduction_blockage")),
90 _k_blockage(getParam<std::vector<Real>>("k_blockage")),
91 _pitch(getParam<Real>("pitch")),
92 _kij(getParam<Real>("Kij")),
93 _pin_diameter(getParam<Real>("pin_diameter")),
94 _n_cells(getParam<unsigned int>("n_cells")),
95 _n_rings(getParam<unsigned int>("nrings")),
96 _n_channels(0),
97 _flat_to_flat(getParam<Real>("flat_to_flat")),
98 _dwire(getParam<Real>("dwire")),
99 _hwire(getParam<Real>("hwire")),
100 _duct_to_pin_gap(0.5 *
101 (_flat_to_flat - (_n_rings - 1) * _pitch * std::sqrt(3.0) - _pin_diameter)),
102 _npins(0),
103 _n_gaps(0)
104{
106
107 if (_n_rings < 2)
108 paramError("nrings",
109 "'nrings' must be at least 2. In this mesh generator, the center pin counts as "
110 "the first ring, so a 7-pin bundle uses nrings = 2.");
111
112 if (_n_cells == 0)
113 paramError("n_cells", "The number of axial cells must be greater than zero");
114
115 if (total_length <= 0.0)
116 mooseError("Total bundle length must be greater than zero");
117
118 if (_spacer_z.size() != _spacer_k.size())
119 mooseError("Size of vector spacer_z should be equal to size of vector spacer_k");
120
121 for (const auto spacer_z : _spacer_z)
122 if (spacer_z < 0.0 || spacer_z > total_length)
123 paramError("spacer_z", "Location of spacers should be between zero and total bundle length");
124
125 if (_z_blockage.size() != 2)
126 paramError("z_blockage", "Size of vector z_blockage must be 2");
127
128 if (_z_blockage.front() > _z_blockage.back())
129 paramError("z_blockage", "z_blockage inlet location must not exceed outlet location");
130
131 if (*max_element(_reduction_blockage.begin(), _reduction_blockage.end()) > 1)
132 paramError("reduction_blockage",
133 "The area reduction of the blocked subchannels cannot be more than 1");
134
135 if ((_index_blockage.size() != _reduction_blockage.size()) ||
136 (_index_blockage.size() != _k_blockage.size()) ||
137 (_reduction_blockage.size() != _k_blockage.size()))
138 mooseError("Size of vectors: index_blockage, reduction_blockage, k_blockage, must be equal "
139 "to eachother");
140
143
144 // Defining the total length from 3 axial sections
145 Real L = total_length;
146
147 // Defining the position of the spacer grid in the numerical solution array
148 std::vector<int> spacer_cell;
149 for (const auto & elem : _spacer_z)
150 spacer_cell.emplace_back(std::round(elem * _n_cells / L));
151
152 // Defining the array for axial resistances
153 std::vector<Real> kgrid;
154 kgrid.resize(_n_cells + 1, 0.0);
155
156 // Summing the spacer resistance to the grid resistance array
157 for (unsigned int index = 0; index < spacer_cell.size(); index++)
158 kgrid[spacer_cell[index]] += _spacer_k[index];
159
160 // compute the hex mesh variables
161 // -------------------------------------------
162 // x coordinate for the first position
163 Real x0 = 0.0;
164 // y coordinate for the first position
165 Real y0 = 0.0;
166 // x coordinate for the second position
167 Real x1 = 0.0;
168 // y coordinate for the second position dummy variable
169 Real y1 = 0.0;
170 // dummy variable
171 Real a1 = 0.0;
172 // dummy variable
173 Real a2 = 0.0;
174 // average x coordinate
175 Real avg_coor_x = 0.0;
176 // average y coordinate
177 Real avg_coor_y = 0.0;
178 // distance between two points
179 Real dist = 0.0;
180 // distance between two points
181 Real dist0 = 0.0;
182 // integer counter
183 unsigned int kgap = 0;
184 // dummy integer
185 unsigned int icorner = 0;
186 // used to defined global direction of the cross_flow_map coefficients for each subchannel and gap
187 const Real positive_flow = 1.0;
188 // used to defined global direction of the cross_flow_map coefficients for each subchannel and gap
189 const Real negative_flow = -1.0;
190 // the indicator used while setting _gap_to_chan_map array
191 std::vector<std::pair<unsigned int, unsigned int>> gap_fill;
193 _npins = _pin_position.size();
194 // assign the pins to the corresponding rings
195 unsigned int k = 0; // initialize the fuel Pin counter index
196 _pins_in_rings.resize(_n_rings);
197 _pins_in_rings[0].push_back(k++);
198 for (unsigned int i = 1; i < _n_rings; i++)
199 for (unsigned int j = 0; j < i * 6; j++)
200 _pins_in_rings[i].push_back(k++);
201 // Given the number of pins and number of fuel Pin rings, the number of subchannels can be
202 // computed as follows:
203 unsigned int chancount = 0.0;
204 // Summing internal channels
205 for (unsigned int j = 0; j < _n_rings - 1; j++)
206 chancount += j * 6;
207 // Adding external channels to the total count
208 _n_channels = chancount + _npins - 1 + (_n_rings - 1) * 6 + 6;
209
210 if (*max_element(_index_blockage.begin(), _index_blockage.end()) > (_n_channels - 1))
211 paramError("index_blockage",
212 "The index of the blocked subchannel cannot be more than the max index of the "
213 "subchannels");
214
215 if ((_index_blockage.size() > _n_channels) || (_reduction_blockage.size() > _n_channels) ||
216 (_k_blockage.size() > _n_channels))
217 mooseError("Size of vectors: index_blockage, reduction_blockage, k_blockage, cannot be more "
218 "than the total number of subchannels");
219
220 // Defining the 2D array for axial resistances
221 _k_grid.resize(_n_channels, std::vector<Real>(_n_cells + 1));
222 for (unsigned int i = 0; i < _n_channels; i++)
223 _k_grid[i] = kgrid;
224
225 // Add blockage resistance to the 2D grid resistane array
226 Real dz = L / _n_cells;
227 for (unsigned int i = 0; i < _n_cells + 1; i++)
228 {
229 if ((dz * i >= _z_blockage.front() && dz * i <= _z_blockage.back()))
230 {
231 unsigned int index(0);
232 for (const auto & i_ch : _index_blockage)
233 {
234 _k_grid[i_ch][i] += _k_blockage[index];
235 index++;
236 }
237 }
238 }
239
241 _pin_to_chan_map.resize(_npins);
242 _subch_type.resize(_n_channels);
243 _n_gaps = _n_channels + _npins - 1;
245 _gap_to_pin_map.resize(_n_gaps);
246 gap_fill.resize(_n_gaps);
250 _gij_map.resize(_n_cells + 1);
252 _gap_type.resize(_n_gaps);
254
255 for (unsigned int i = 0; i < _n_channels; i++)
256 {
257 _chan_to_pin_map[i].reserve(3);
258 _chan_to_gap_map[i].reserve(3);
259 _sign_id_crossflow_map[i].reserve(3);
260 _subchannel_position[i].reserve(3);
261 for (unsigned int j = 0; j < 3; j++)
262 {
263 _sign_id_crossflow_map.at(i).push_back(positive_flow);
264 _subchannel_position.at(i).push_back(0.0);
265 }
266 }
267
268 for (unsigned int iz = 0; iz < _n_cells + 1; iz++)
269 {
270 _gij_map[iz].reserve(_n_gaps);
271 }
272
273 for (unsigned int i = 0; i < _npins; i++)
274 _pin_to_chan_map[i].reserve(6);
275
276 // create the subchannels
277 k = 0; // initialize the subchannel counter index
278 kgap = 0;
279 // for each ring we trace the subchannels by pairing up to neighbor pins and looking for the third
280 // Pin at inner or outer ring compared to the current ring.
281 for (unsigned int i = 1; i < _n_rings; i++)
282 {
283 // find the closest Pin at back ring
284 for (unsigned int j = 0; j < _pins_in_rings[i].size(); j++)
285 {
286 if (j == _pins_in_rings[i].size() - 1)
287 {
288 _chan_to_pin_map[k].push_back(_pins_in_rings[i][j]);
289 _chan_to_pin_map[k].push_back(_pins_in_rings[i][0]);
290 avg_coor_x =
291 0.5 * (_pin_position[_pins_in_rings[i][j]](0) + _pin_position[_pins_in_rings[i][0]](0));
292 avg_coor_y =
293 0.5 * (_pin_position[_pins_in_rings[i][j]](1) + _pin_position[_pins_in_rings[i][0]](1));
294 _gap_to_pin_map[kgap].first = _pins_in_rings[i][0];
295 _gap_to_pin_map[kgap].second = _pins_in_rings[i][j];
297 kgap = kgap + 1;
298 }
299 else
300 {
301 _chan_to_pin_map[k].push_back(_pins_in_rings[i][j]);
302 _chan_to_pin_map[k].push_back(_pins_in_rings[i][j + 1]);
303 avg_coor_x = 0.5 * (_pin_position[_pins_in_rings[i][j]](0) +
304 _pin_position[_pins_in_rings[i][j + 1]](0));
305 avg_coor_y = 0.5 * (_pin_position[_pins_in_rings[i][j]](1) +
306 _pin_position[_pins_in_rings[i][j + 1]](1));
307 _gap_to_pin_map[kgap].first = _pins_in_rings[i][j];
308 _gap_to_pin_map[kgap].second = _pins_in_rings[i][j + 1];
310 kgap = kgap + 1;
311 }
312
313 dist0 = 1.0e+5;
314
315 _chan_to_pin_map[k].push_back(_pins_in_rings[i - 1][0]);
316 unsigned int l0 = 0;
317
318 for (unsigned int l = 0; l < _pins_in_rings[i - 1].size(); l++)
319 {
320 dist = std::sqrt(pow(_pin_position[_pins_in_rings[i - 1][l]](0) - avg_coor_x, 2) +
321 pow(_pin_position[_pins_in_rings[i - 1][l]](1) - avg_coor_y, 2));
322
323 if (dist < dist0)
324 {
325 _chan_to_pin_map[k][2] = _pins_in_rings[i - 1][l];
326 l0 = l;
327 dist0 = dist;
328 } // if
329 } // l
330
331 _gap_to_pin_map[kgap].first = _pins_in_rings[i][j];
332 _gap_to_pin_map[kgap].second = _pins_in_rings[i - 1][l0];
334 kgap = kgap + 1;
336 k = k + 1;
337 } // for j
338
339 // find the closest Pin at front ring
340 for (unsigned int j = 0; j < _pins_in_rings[i].size(); j++)
341 {
342 if (j == _pins_in_rings[i].size() - 1)
343 {
344 _chan_to_pin_map[k].push_back(_pins_in_rings[i][j]);
345 _chan_to_pin_map[k].push_back(_pins_in_rings[i][0]);
346 avg_coor_x =
347 0.5 * (_pin_position[_pins_in_rings[i][j]](0) + _pin_position[_pins_in_rings[i][0]](0));
348 avg_coor_y =
349 0.5 * (_pin_position[_pins_in_rings[i][j]](1) + _pin_position[_pins_in_rings[i][0]](1));
350 }
351 else
352 {
353 _chan_to_pin_map[k].push_back(_pins_in_rings[i][j]);
354 _chan_to_pin_map[k].push_back(_pins_in_rings[i][j + 1]);
355 avg_coor_x = 0.5 * (_pin_position[_pins_in_rings[i][j]](0) +
356 _pin_position[_pins_in_rings[i][j + 1]](0));
357 avg_coor_y = 0.5 * (_pin_position[_pins_in_rings[i][j]](1) +
358 _pin_position[_pins_in_rings[i][j + 1]](1));
359 }
360
361 // if the outermost ring, set the edge subchannels first... then the corner subchannels
362 if (i == _n_rings - 1)
363 {
364 // add edges
365 _subch_type[k] = EChannelType::EDGE; // an edge subchannel is created
366 _gap_to_pin_map[kgap].first = _pins_in_rings[i][j];
367 _gap_to_pin_map[kgap].second = _pins_in_rings[i][j];
369 _chan_to_gap_map[k].push_back(kgap);
370 kgap = kgap + 1;
371 k = k + 1;
372
373 if (j % i == 0)
374 {
375 // generate a corner subchannel, generate the additional gap and fix chan_to_gap_map
376 _gap_to_pin_map[kgap].first = _pins_in_rings[i][j];
377 _gap_to_pin_map[kgap].second = _pins_in_rings[i][j];
379
380 // corner subchannel
381 _chan_to_pin_map[k].push_back(_pins_in_rings[i][j]);
382 _chan_to_gap_map[k].push_back(kgap - 1);
383 _chan_to_gap_map[k].push_back(kgap);
385
386 kgap = kgap + 1;
387 k = k + 1;
388 }
389 // if not the outer most ring
390 }
391 else
392 {
393 dist0 = 1.0e+5;
394 unsigned int l0 = 0;
395 _chan_to_pin_map[k].push_back(_pins_in_rings[i + 1][0]);
396 for (unsigned int l = 0; l < _pins_in_rings[i + 1].size(); l++)
397 {
398 dist = std::sqrt(pow(_pin_position[_pins_in_rings[i + 1][l]](0) - avg_coor_x, 2) +
399 pow(_pin_position[_pins_in_rings[i + 1][l]](1) - avg_coor_y, 2));
400 if (dist < dist0)
401 {
402 _chan_to_pin_map[k][2] = _pins_in_rings[i + 1][l];
403 dist0 = dist;
404 l0 = l;
405 } // if
406 } // l
407
408 _gap_to_pin_map[kgap].first = _pins_in_rings[i][j];
409 _gap_to_pin_map[kgap].second = _pins_in_rings[i + 1][l0];
411 kgap = kgap + 1;
413 k = k + 1;
414 } // if
415 } // for j
416 } // for i
417
418 // Constructing pins to channels mao
419 for (unsigned int loc_rod = 0; loc_rod < _npins; loc_rod++)
420 {
421 for (unsigned int i = 0; i < _n_channels; i++)
422 {
423 bool rod_in_sc = false;
424 for (unsigned int j : _chan_to_pin_map[i])
425 {
426 if (j == loc_rod)
427 rod_in_sc = true;
428 }
429 if (rod_in_sc)
430 {
431 _pin_to_chan_map[loc_rod].push_back(i);
432 }
433 }
434 }
435
448 for (unsigned int i = 0; i < _n_channels; i++)
449 {
451 {
452 for (unsigned int j = 0; j < _n_gaps; j++)
453 {
455 {
456 if (((_chan_to_pin_map[i][0] == _gap_to_pin_map[j].first) &&
457 (_chan_to_pin_map[i][1] == _gap_to_pin_map[j].second)) ||
458 ((_chan_to_pin_map[i][0] == _gap_to_pin_map[j].second) &&
459 (_chan_to_pin_map[i][1] == _gap_to_pin_map[j].first)))
460 {
461 _chan_to_gap_map[i].push_back(j);
462 }
463
464 if (((_chan_to_pin_map[i][0] == _gap_to_pin_map[j].first) &&
465 (_chan_to_pin_map[i][2] == _gap_to_pin_map[j].second)) ||
466 ((_chan_to_pin_map[i][0] == _gap_to_pin_map[j].second) &&
467 (_chan_to_pin_map[i][2] == _gap_to_pin_map[j].first)))
468 {
469 _chan_to_gap_map[i].push_back(j);
470 }
471
472 if (((_chan_to_pin_map[i][1] == _gap_to_pin_map[j].first) &&
473 (_chan_to_pin_map[i][2] == _gap_to_pin_map[j].second)) ||
474 ((_chan_to_pin_map[i][1] == _gap_to_pin_map[j].second) &&
475 (_chan_to_pin_map[i][2] == _gap_to_pin_map[j].first)))
476 {
477 _chan_to_gap_map[i].push_back(j);
478 }
479 }
480 } // for j
481 }
482 else if (_subch_type[i] == EChannelType::EDGE)
483 {
484 for (unsigned int j = 0; j < _n_gaps; j++)
485 {
487 {
488 if (((_chan_to_pin_map[i][0] == _gap_to_pin_map[j].first) &&
489 (_chan_to_pin_map[i][1] == _gap_to_pin_map[j].second)) ||
490 ((_chan_to_pin_map[i][0] == _gap_to_pin_map[j].second) &&
491 (_chan_to_pin_map[i][1] == _gap_to_pin_map[j].first)))
492 {
493 _chan_to_gap_map[i].push_back(j);
494 }
495 }
496 }
497
498 icorner = 0;
499 for (unsigned int k = 0; k < _n_channels; k++)
500 {
502 _chan_to_pin_map[i][1] == _chan_to_pin_map[k][0])
503 {
504 _chan_to_gap_map[i].push_back(_chan_to_gap_map[k][1]);
505 icorner = 1;
506 break;
507 } // if
508 } // for
509
510 // Check whether the edge channel's first pin is also a corner pin. This second corner lookup
511 // is only needed while the edge channel still needs another perimeter gap.
512 if (_chan_to_gap_map[i].size() < 3)
513 {
514 for (unsigned int k = 0; k < _n_channels; k++)
515 {
517 _chan_to_pin_map[i][0] == _chan_to_pin_map[k][0])
518 {
519 _chan_to_gap_map[i].push_back(_chan_to_gap_map[k][1] + 1);
520 icorner = 1;
521 break;
522 }
523 }
524 }
525
526 if (icorner == 0)
527 {
528 _chan_to_gap_map[i].push_back(_chan_to_gap_map[i][0] + 1);
529 }
530 }
531 }
532
533 // find gap_to_chan_map pair
534 for (unsigned int j = 0; j < _n_gaps; j++)
535 {
536 for (unsigned int i = 0; i < _n_channels; i++)
537 {
539 {
540 if ((j == _chan_to_gap_map[i][0]) || (j == _chan_to_gap_map[i][1]) ||
541 (j == _chan_to_gap_map[i][2]))
542 {
543 if (_gap_to_chan_map[j].first == 0 && gap_fill[j].first == 0)
544 {
545 _gap_to_chan_map[j].first = i;
546 gap_fill[j].first = 1;
547 }
548 else if (_gap_to_chan_map[j].second == 0 && gap_fill[j].second == 0)
549 {
550 _gap_to_chan_map[j].second = i;
551 gap_fill[j].second = 1;
552 }
553 else
554 {
555 }
556 }
557 }
558 else if (_subch_type[i] == EChannelType::CORNER)
559 {
560 if ((j == _chan_to_gap_map[i][0]) || (j == _chan_to_gap_map[i][1]))
561 {
562 if (_gap_to_chan_map[j].first == 0 && gap_fill[j].first == 0)
563 {
564 _gap_to_chan_map[j].first = i;
565 gap_fill[j].first = 1;
566 }
567 else if (_gap_to_chan_map[j].second == 0 && gap_fill[j].second == 0)
568 {
569 _gap_to_chan_map[j].second = i;
570 gap_fill[j].second = 1;
571 }
572 else
573 {
574 }
575 }
576 }
577 } // i
578 } // j
579
580 for (unsigned int k = 0; k < _n_channels; k++)
581 {
583 {
584 _gap_pairs_sf[k].first = _chan_to_gap_map[k][0];
585 _gap_pairs_sf[k].second = _chan_to_gap_map[k][2];
586 auto k1 = _gap_pairs_sf[k].first;
587 auto k2 = _gap_pairs_sf[k].second;
588 if (_gap_to_chan_map[k1].first == k)
589 {
590 _chan_pairs_sf[k].first = _gap_to_chan_map[k1].second;
591 }
592 else
593 {
594 _chan_pairs_sf[k].first = _gap_to_chan_map[k1].first;
595 }
596
597 if (_gap_to_chan_map[k2].first == k)
598 {
599 _chan_pairs_sf[k].second = _gap_to_chan_map[k2].second;
600 }
601 else
602 {
603 _chan_pairs_sf[k].second = _gap_to_chan_map[k2].first;
604 }
605 }
606 else if (_subch_type[k] == EChannelType::CORNER)
607 {
608 _gap_pairs_sf[k].first = _chan_to_gap_map[k][1];
609 _gap_pairs_sf[k].second = _chan_to_gap_map[k][0];
610
611 auto k1 = _gap_pairs_sf[k].first;
612 auto k2 = _gap_pairs_sf[k].second;
613
614 if (_gap_to_chan_map[k1].first == k)
615 {
616 _chan_pairs_sf[k].first = _gap_to_chan_map[k1].second;
617 }
618 else
619 {
620 _chan_pairs_sf[k].first = _gap_to_chan_map[k1].first;
621 }
622
623 if (_gap_to_chan_map[k2].first == k)
624 {
625 _chan_pairs_sf[k].second = _gap_to_chan_map[k2].second;
626 }
627 else
628 {
629 _chan_pairs_sf[k].second = _gap_to_chan_map[k2].first;
630 }
631 }
632 }
633
634 // set the _gij_map
635 for (unsigned int iz = 0; iz < _n_cells + 1; iz++)
636 {
637 for (unsigned int i_gap = 0; i_gap < _n_gaps; i_gap++)
638 {
639 if (_gap_type[i_gap] == EChannelType::CENTER)
640 {
641 _gij_map[iz].push_back(_pitch - _pin_diameter);
642 }
643 else if (_gap_type[i_gap] == EChannelType::EDGE || _gap_type[i_gap] == EChannelType::CORNER)
644 {
645 _gij_map[iz].push_back(_duct_to_pin_gap);
646 }
647 }
648 }
649
650 for (unsigned int i = 0; i < _n_channels; i++)
651 {
653 {
654 for (unsigned int k = 0; k < 3; k++)
655 {
656 for (unsigned int j = 0; j < _n_gaps; j++)
657 {
658 if (_chan_to_gap_map[i][k] == j && i == _gap_to_chan_map[j].first)
659 {
660 if (i > _gap_to_chan_map[j].second)
661 {
662 _sign_id_crossflow_map[i][k] = negative_flow;
663 }
664 else
665 {
666 _sign_id_crossflow_map[i][k] = positive_flow;
667 }
668 }
669 else if (_chan_to_gap_map[i][k] == j && i == _gap_to_chan_map[j].second)
670 {
671 if (i > _gap_to_chan_map[j].first)
672 {
673 _sign_id_crossflow_map[i][k] = negative_flow;
674 }
675 else
676 {
677 _sign_id_crossflow_map[i][k] = positive_flow;
678 }
679 }
680 } // j
681 } // k
682 }
683 else if (_subch_type[i] == EChannelType::CORNER)
684 {
685 for (unsigned int k = 0; k < 2; k++)
686 {
687 for (unsigned int j = 0; j < _n_gaps; j++)
688 {
689 if (_chan_to_gap_map[i][k] == j && i == _gap_to_chan_map[j].first)
690 {
691 if (i > _gap_to_chan_map[j].second)
692 {
693 _sign_id_crossflow_map[i][k] = negative_flow;
694 }
695 else
696 {
697 _sign_id_crossflow_map[i][k] = positive_flow;
698 }
699 }
700 else if (_chan_to_gap_map[i][k] == j && i == _gap_to_chan_map[j].second)
701 {
702 if (i > _gap_to_chan_map[j].first)
703 {
704 _sign_id_crossflow_map[i][k] = negative_flow;
705 }
706 else
707 {
708 _sign_id_crossflow_map[i][k] = positive_flow;
709 }
710 }
711 } // j
712 } // k
713 } // subch_type =2
714 } // i
715
716 // set the subchannel positions
717 for (unsigned int i = 0; i < _n_channels; i++)
718 {
720 {
724 3.0;
728 3.0;
729 }
730 else if (_subch_type[i] == EChannelType::EDGE)
731 {
732 for (unsigned int j = 0; j < _n_channels; j++)
733 {
735 ((_chan_to_pin_map[i][0] == _chan_to_pin_map[j][0] &&
736 _chan_to_pin_map[i][1] == _chan_to_pin_map[j][1]) ||
737 (_chan_to_pin_map[i][0] == _chan_to_pin_map[j][1] &&
738 _chan_to_pin_map[i][1] == _chan_to_pin_map[j][0])))
739 {
740 x0 = _pin_position[_chan_to_pin_map[j][2]](0);
741 y0 = _pin_position[_chan_to_pin_map[j][2]](1);
742 }
743 else if (_subch_type[j] == EChannelType::CENTER &&
744 ((_chan_to_pin_map[i][0] == _chan_to_pin_map[j][0] &&
745 _chan_to_pin_map[i][1] == _chan_to_pin_map[j][2]) ||
746 (_chan_to_pin_map[i][0] == _chan_to_pin_map[j][2] &&
747 _chan_to_pin_map[i][1] == _chan_to_pin_map[j][0])))
748 {
749 x0 = _pin_position[_chan_to_pin_map[j][1]](0);
750 y0 = _pin_position[_chan_to_pin_map[j][1]](1);
751 }
752 else if (_subch_type[j] == EChannelType::CENTER &&
753 ((_chan_to_pin_map[i][0] == _chan_to_pin_map[j][1] &&
754 _chan_to_pin_map[i][1] == _chan_to_pin_map[j][2]) ||
755 (_chan_to_pin_map[i][0] == _chan_to_pin_map[j][2] &&
756 _chan_to_pin_map[i][1] == _chan_to_pin_map[j][1])))
757 {
758 x0 = _pin_position[_chan_to_pin_map[j][0]](0);
759 y0 = _pin_position[_chan_to_pin_map[j][0]](1);
760 }
761 x1 = 0.5 *
763 y1 = 0.5 *
765 a1 = _pin_diameter / 2.0 + _duct_to_pin_gap / 2.0;
766 a2 = std::sqrt((x1 - x0) * (x1 - x0) + (y1 - y0) * (y1 - y0)) + a1;
767 _subchannel_position[i][0] = (a2 * x1 - a1 * x0) / (a2 - a1);
768 _subchannel_position[i][1] = (a2 * y1 - a1 * y0) / (a2 - a1);
769 } // j
770 }
771 else if (_subch_type[i] == EChannelType::CORNER)
772 {
773 x0 = _pin_position[0](0);
774 y0 = _pin_position[0](1);
775 x1 = _pin_position[_chan_to_pin_map[i][0]](0);
776 y1 = _pin_position[_chan_to_pin_map[i][0]](1);
777 a1 = _pin_diameter / 2.0 + _duct_to_pin_gap / 2.0;
778 a2 = std::sqrt((x1 - x0) * (x1 - x0) + (y1 - y0) * (y1 - y0)) + a1;
779 _subchannel_position[i][0] = (a2 * x1 - a1 * x0) / (a2 - a1);
780 _subchannel_position[i][1] = (a2 * y1 - a1 * y0) / (a2 - a1);
781 }
782 }
783
784 // Reduce reserved memory in the channel-to-gap map.
785 for (auto & gap : _chan_to_gap_map)
786 {
787 gap.shrink_to_fit();
788 }
789}
ExpressionBuilder::EBTerm pow(const ExpressionBuilder::EBTerm &left, T exponent)
void paramError(const std::string &param, Args... args) const
void mooseError(Args &&... args) const
const T & getParam(const std::string &name) const
const std::vector< Real > _reduction_blockage
area reduction of subchannels affected by blockage
std::vector< std::vector< Real > > _sign_id_crossflow_map
Defines the global cross-flow direction -1 or 1 for each subchannel and for all gaps that are belongi...
const Real _pitch
Distance between the neighbor fuel pins, pitch.
const unsigned int _n_rings
number of rings of fuel pins
std::vector< std::vector< unsigned int > > _pin_to_chan_map
stores the map from pins to channels
const std::vector< Real > _k_blockage
form loss coefficient of subchannels affected by blockage
std::vector< std::pair< unsigned int, unsigned int > > _gap_to_pin_map
stores the fuel pin pairs for each gap each gap
std::vector< std::vector< Real > > _subchannel_position
x,y coordinates of the subchannel centroids
const Real _heated_length
heated length of the fuel Pin
std::vector< std::pair< unsigned int, unsigned int > > _gap_pairs_sf
sweeping flow model gap pairs per channel to specify directional edge flow
std::vector< std::vector< Real > > _k_grid
axial form loss coefficient per computational cell
const std::vector< Real > & _spacer_k
form loss coefficient of the spacers
const Real _flat_to_flat
the distance between flat surfaces of the duct facing each other
const unsigned int _pin_block_id
pin block index
const std::vector< Real > _z_blockage
axial location of blockage (inlet, outlet) [m]
unsigned int _n_channels
number of subchannels
std::vector< std::pair< unsigned int, unsigned int > > _chan_pairs_sf
sweeping flow model channel pairs to specify directional edge flow
const std::vector< Real > & _spacer_z
axial location of the spacers
std::vector< std::vector< Real > > _pins_in_rings
fuel pins that are belonging to each ring
const Real _unheated_length_exit
unheated length of the fuel Pin at the exit of the assembly
std::vector< EChannelType > _subch_type
subchannel type
const unsigned int _subchannel_block_id
subchannel block index
std::vector< std::vector< Real > > _gij_map
gap size
std::vector< std::vector< unsigned int > > _chan_to_gap_map
stores the gaps that forms each subchannel
std::vector< Real > _z_grid
axial location of nodes
unsigned int _npins
number of fuel pins
std::vector< EChannelType > _gap_type
gap type
const Real _pin_diameter
fuel Pin diameter
const Real _duct_to_pin_gap
the gap thickness between the duct and peripheral fuel pins
const std::vector< unsigned int > _index_blockage
index of subchannels affected by blockage
const Real _unheated_length_entry
unheated length of the fuel Pin at the entry of the assembly
const Real & _kij
Lateral form loss coefficient.
std::vector< std::pair< unsigned int, unsigned int > > _gap_to_chan_map
stores the channel pairs for each gap
std::vector< Point > _pin_position
x,y coordinates of the fuel pins
std::vector< std::vector< unsigned int > > _chan_to_pin_map
stores the fuel pins belonging to each subchannel
const unsigned int _n_cells
number of axial cells
static void generateZGrid(Real unheated_length_entry, Real heated_length, Real unheated_length_exit, unsigned int n_cells, std::vector< Real > &z_grid)
Generate the spacing in z-direction using heated and unteaded lengths.
static void pinPositions(std::vector< Point > &positions, unsigned int nrings, Real pitch, Point center)
Calculates and stores the pin positions/centers for a hexagonal assembly containing the given number ...
T round(T x)
if(subdm)
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real

Member Function Documentation

◆ buildPinMesh()

void SCMTriAssemblyMeshGenerator::buildPinMesh ( MeshBase &  mesh_base)
protected

Build the 1D pin elements and append them to the subchannel mesh.

Definition at line 792 of file SCMTriAssemblyMeshGenerator.C.

793{
794 if (_npins == 0)
795 return;
796
797 mesh_base.reserve_elem(_n_cells * _npins);
798 mesh_base.reserve_nodes((_n_cells + 1) * _npins);
799
800 _pin_nodes.clear();
801 _pin_nodes.resize(_npins);
802
803 // Defining the extent of the subchannel mesh to append the pin mesh to the current subchannel
804 // mesh.
805 const unsigned int node_sub = mesh_base.n_nodes();
806 const unsigned int elem_sub = mesh_base.n_elem();
807
808 // Add the points in the shape of a rectilinear grid. The grid is regular on the xy-plane at the
809 // triangular lattice pin positions. The grid along z is also regular. Store pointers in the
810 // _pin_nodes array so we can keep track of which points are in which pins.
811 unsigned int node_id = node_sub;
812 for (unsigned int i = 0; i < _npins; i++)
813 {
814 _pin_nodes[i].reserve(_n_cells + 1);
815 for (unsigned int iz = 0; iz < _n_cells + 1; iz++)
816 _pin_nodes[i].push_back(mesh_base.add_point(
817 Point(_pin_position[i](0), _pin_position[i](1), _z_grid[iz]), node_id++));
818 }
819
820 // Add the elements which in this case are 2-node edges that link each pin's nodes vertically.
821 unsigned int elem_id = elem_sub;
822 for (unsigned int i = 0; i < _npins; i++)
823 for (unsigned int iz = 0; iz < _n_cells; iz++)
824 {
825 Elem * elem = mesh_base.add_elem(std::make_unique<Edge2>());
826 elem->subdomain_id() = _pin_block_id;
827 elem->set_id(elem_id++);
828 const int indx1 = (_n_cells + 1) * i + iz + node_sub;
829 const int indx2 = (_n_cells + 1) * i + (iz + 1) + node_sub;
830 elem->set_node(0, mesh_base.node_ptr(indx1));
831 elem->set_node(1, mesh_base.node_ptr(indx2));
832 }
833
834 mesh_base.set_subdomain_name(_pin_block_id, "fuel_pins", true);
835}
std::vector< std::vector< Node * > > _pin_nodes
pin nodes

Referenced by generate().

◆ generate()

std::unique_ptr< MeshBase > SCMTriAssemblyMeshGenerator::generate ( )
overridevirtual

Implements MeshGenerator.

Definition at line 838 of file SCMTriAssemblyMeshGenerator.C.

839{
840 auto mesh_base = buildMeshBaseObject();
841
842 BoundaryInfo & boundary_info = mesh_base->get_boundary_info();
843 mesh_base->set_spatial_dimension(3);
844 mesh_base->reserve_elem(_n_cells * (_n_channels + _npins));
845 mesh_base->reserve_nodes((_n_cells + 1) * (_n_channels + _npins));
846 _nodes.resize(_n_channels);
847 // Add the points for the give x,y subchannel positions. The grid is hexagonal.
848 // The grid along
849 // z is irregular to account for Pin spacers. Store pointers in the _nodes
850 // array so we can keep track of which points are in which channels.
851 unsigned int node_id = 0;
852 for (unsigned int i = 0; i < _n_channels; i++)
853 {
854 _nodes[i].reserve(_n_cells + 1);
855 for (unsigned int iz = 0; iz < _n_cells + 1; iz++)
856 {
857 _nodes[i].push_back(mesh_base->add_point(
858 Point(_subchannel_position[i][0], _subchannel_position[i][1], _z_grid[iz]), node_id++));
859 }
860 }
861
862 // Add the elements which in this case are 2-node edges that link each
863 // subchannel's nodes vertically.
864 unsigned int elem_id = 0;
865 for (unsigned int i = 0; i < _n_channels; i++)
866 {
867 for (unsigned int iz = 0; iz < _n_cells; iz++)
868 {
869 Elem * elem = mesh_base->add_elem(std::make_unique<Edge2>());
870 elem->subdomain_id() = _subchannel_block_id;
871 elem->set_id(elem_id++);
872 const int indx1 = (_n_cells + 1) * i + iz;
873 const int indx2 = (_n_cells + 1) * i + (iz + 1);
874 elem->set_node(0, mesh_base->node_ptr(indx1));
875 elem->set_node(1, mesh_base->node_ptr(indx2));
876
877 if (iz == 0)
878 boundary_info.add_side(elem, 0, 0);
879 if (iz == _n_cells - 1)
880 boundary_info.add_side(elem, 1, 1);
881 }
882 }
883 boundary_info.sideset_name(0) = "inlet";
884 boundary_info.sideset_name(1) = "outlet";
885 boundary_info.nodeset_name(0) = "inlet";
886 boundary_info.nodeset_name(1) = "outlet";
887
888 // Naming the block
889 mesh_base->set_subdomain_name(_subchannel_block_id, "subchannel", true);
890 buildPinMesh(*mesh_base);
891
892 mesh_base->prepare_for_use();
893
894 // move the meta data into TriSubChannelMesh
895 auto & sch_mesh = static_cast<TriSubChannelMesh &>(*_mesh);
897 sch_mesh._heated_length = _heated_length;
898 sch_mesh._unheated_length_exit = _unheated_length_exit;
899 sch_mesh._z_grid = _z_grid;
900 sch_mesh._k_grid = _k_grid;
901 sch_mesh._spacer_z = _spacer_z;
902 sch_mesh._spacer_k = _spacer_k;
903 sch_mesh._z_blockage = _z_blockage;
904 sch_mesh._index_blockage = _index_blockage;
905 sch_mesh._reduction_blockage = _reduction_blockage;
906 sch_mesh._kij = _kij;
907 sch_mesh._pitch = _pitch;
908 sch_mesh._pin_diameter = _pin_diameter;
909 sch_mesh._n_cells = _n_cells;
910 sch_mesh._n_rings = _n_rings;
911 sch_mesh._n_channels = _n_channels;
912 sch_mesh._flat_to_flat = _flat_to_flat;
913 sch_mesh._dwire = _dwire;
914 sch_mesh._hwire = _hwire;
915 sch_mesh._duct_to_pin_gap = _duct_to_pin_gap;
916 sch_mesh._nodes = _nodes;
917 sch_mesh._gap_to_chan_map = _gap_to_chan_map;
918 sch_mesh._gap_to_pin_map = _gap_to_pin_map;
919 sch_mesh._chan_to_gap_map = _chan_to_gap_map;
920 sch_mesh._sign_id_crossflow_map = _sign_id_crossflow_map;
921 sch_mesh._gij_map = _gij_map;
922 sch_mesh._subchannel_position = _subchannel_position;
923 sch_mesh._pin_position = _pin_position;
924 sch_mesh._pins_in_rings = _pins_in_rings;
925 sch_mesh._chan_to_pin_map = _chan_to_pin_map;
926 sch_mesh._npins = _npins;
927 sch_mesh._n_gaps = _n_gaps;
928 sch_mesh._subch_type = _subch_type;
929 sch_mesh._gap_type = _gap_type;
930 sch_mesh._gap_pairs_sf = _gap_pairs_sf;
931 sch_mesh._chan_pairs_sf = _chan_pairs_sf;
932 sch_mesh._pin_to_chan_map = _pin_to_chan_map;
933 sch_mesh._pin_nodes = _pin_nodes;
934 sch_mesh._pin_mesh_exist = (_npins > 0);
935 sch_mesh.computeAssemblyHydraulicParameters();
936
937 return mesh_base;
938}
std::unique_ptr< MeshBase > buildMeshBaseObject(unsigned int dim=libMesh::invalid_uint)
void buildPinMesh(MeshBase &mesh_base)
Build the 1D pin elements and append them to the subchannel mesh.
std::vector< std::vector< Node * > > _nodes
nodes
Real _unheated_length_entry
unheated length of the fuel Pin at the entry of the assembly
Mesh class for triangular, edge and corner subchannels for hexagonal lattice fuel assemblies.

◆ validParams()

InputParameters SCMTriAssemblyMeshGenerator::validParams ( )
static

Definition at line 36 of file SCMTriAssemblyMeshGenerator.C.

37{
40 "Creates a mesh of 1D subchannels and 1D pins in a triangular lattice arrangement");
41 params.addRequiredParam<unsigned int>("n_cells", "The number of cells in the axial direction");
42 params.addRequiredParam<Real>("pitch", "Pitch [m]");
43 params.addRequiredParam<Real>("pin_diameter", "Rod diameter [m]");
44 params.addParam<Real>("unheated_length_entry", 0.0, "Unheated length at entry [m]");
45 params.addRequiredParam<Real>("heated_length", "Heated length [m]");
46 params.addParam<Real>("unheated_length_exit", 0.0, "Unheated length at exit [m]");
47 params.addRequiredParam<unsigned int>(
48 "nrings",
49 "Number of fuel-pin rings per assembly, counting the center pin as the first ring [-]");
50 params.addRequiredParam<Real>("flat_to_flat",
51 "Flat to flat distance for the hexagonal assembly [m]");
52 params.addRequiredParam<Real>("dwire", "Wire diameter [m]");
53 params.addRequiredParam<Real>("hwire", "Wire lead length [m]");
54 params.addParam<std::vector<Real>>(
55 "spacer_z", {}, "Axial location of spacers/vanes/mixing vanes [m]");
56 params.addParam<std::vector<Real>>(
57 "spacer_k", {}, "K-loss coefficient of spacers/vanes/mixing vanes [-]");
58 params.addParam<Real>("Kij", 0.5, "Lateral form loss coefficient [-]");
59 params.addParam<std::vector<Real>>("z_blockage",
60 std::vector<Real>({0.0, 0.0}),
61 "axial location of blockage (inlet, outlet) [m]");
62 params.addParam<std::vector<unsigned int>>("index_blockage",
63 std::vector<unsigned int>({0}),
64 "index of subchannels affected by blockage");
65 params.addParam<std::vector<Real>>(
66 "reduction_blockage",
67 std::vector<Real>({1.0}),
68 "Area reduction of subchannels affected by blockage (number to muliply the area)");
69 params.addParam<std::vector<Real>>("k_blockage",
70 std::vector<Real>({0.0}),
71 "Form loss coefficient of subchannels affected by blockage");
72 params.addParam<unsigned int>("block_id", 0, "Subchannel block id");
73 params.deprecateParam("block_id", "subchannel_block_id", "07/01/2027");
74 params.addParam<unsigned int>("pin_block_id", 1, "Fuel Pin block id");
75 return params;
76}
void addRequiredParam(const std::string &name, const std::string &doc_string)
void addParam(const std::string &name, const std::initializer_list< typename T::value_type > &value, const std::string &doc_string)
void addClassDescription(const std::string &doc_string)
void deprecateParam(const std::string &old_name, const std::string &new_name, const std::string &removal_date)
static InputParameters validParams()

Member Data Documentation

◆ _chan_pairs_sf

std::vector<std::pair<unsigned int, unsigned int> > SCMTriAssemblyMeshGenerator::_chan_pairs_sf
protected

sweeping flow model channel pairs to specify directional edge flow

Definition at line 115 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _chan_to_gap_map

std::vector<std::vector<unsigned int> > SCMTriAssemblyMeshGenerator::_chan_to_gap_map
protected

stores the gaps that forms each subchannel

Definition at line 86 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _chan_to_pin_map

std::vector<std::vector<unsigned int> > SCMTriAssemblyMeshGenerator::_chan_to_pin_map
protected

stores the fuel pins belonging to each subchannel

Definition at line 101 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _duct_to_pin_gap

const Real SCMTriAssemblyMeshGenerator::_duct_to_pin_gap
protected

the gap thickness between the duct and peripheral fuel pins

Definition at line 75 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _dwire

const Real SCMTriAssemblyMeshGenerator::_dwire
protected

wire diameter

Definition at line 71 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate().

◆ _flat_to_flat

const Real SCMTriAssemblyMeshGenerator::_flat_to_flat
protected

the distance between flat surfaces of the duct facing each other

Definition at line 69 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate().

◆ _gap_pairs_sf

std::vector<std::pair<unsigned int, unsigned int> > SCMTriAssemblyMeshGenerator::_gap_pairs_sf
protected

sweeping flow model gap pairs per channel to specify directional edge flow

Definition at line 113 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _gap_to_chan_map

std::vector<std::pair<unsigned int, unsigned int> > SCMTriAssemblyMeshGenerator::_gap_to_chan_map
protected

stores the channel pairs for each gap

Definition at line 82 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _gap_to_pin_map

std::vector<std::pair<unsigned int, unsigned int> > SCMTriAssemblyMeshGenerator::_gap_to_pin_map
protected

stores the fuel pin pairs for each gap each gap

Definition at line 84 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _gap_type

std::vector<EChannelType> SCMTriAssemblyMeshGenerator::_gap_type
protected

gap type

Definition at line 111 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _gij_map

std::vector<std::vector<Real> > SCMTriAssemblyMeshGenerator::_gij_map
protected

gap size

Definition at line 93 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _heated_length

const Real SCMTriAssemblyMeshGenerator::_heated_length
protected

heated length of the fuel Pin

Definition at line 33 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _hwire

const Real SCMTriAssemblyMeshGenerator::_hwire
protected

wire lead length

Definition at line 73 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate().

◆ _index_blockage

const std::vector<unsigned int> SCMTriAssemblyMeshGenerator::_index_blockage
protected

index of subchannels affected by blockage

Definition at line 51 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _k_blockage

const std::vector<Real> SCMTriAssemblyMeshGenerator::_k_blockage
protected

form loss coefficient of subchannels affected by blockage

Definition at line 55 of file SCMTriAssemblyMeshGenerator.h.

Referenced by SCMTriAssemblyMeshGenerator().

◆ _k_grid

std::vector<std::vector<Real> > SCMTriAssemblyMeshGenerator::_k_grid
protected

axial form loss coefficient per computational cell

Definition at line 43 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _kij

const Real& SCMTriAssemblyMeshGenerator::_kij
protected

Lateral form loss coefficient.

Definition at line 59 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate().

◆ _n_cells

const unsigned int SCMTriAssemblyMeshGenerator::_n_cells
protected

number of axial cells

Definition at line 63 of file SCMTriAssemblyMeshGenerator.h.

Referenced by buildPinMesh(), generate(), and SCMTriAssemblyMeshGenerator().

◆ _n_channels

unsigned int SCMTriAssemblyMeshGenerator::_n_channels
protected

number of subchannels

Definition at line 67 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _n_gaps

unsigned int SCMTriAssemblyMeshGenerator::_n_gaps
protected

number of gaps

Definition at line 107 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _n_rings

const unsigned int SCMTriAssemblyMeshGenerator::_n_rings
protected

number of rings of fuel pins

Definition at line 65 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _nodes

std::vector<std::vector<Node *> > SCMTriAssemblyMeshGenerator::_nodes
protected

nodes

Definition at line 78 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate().

◆ _npins

unsigned int SCMTriAssemblyMeshGenerator::_npins
protected

number of fuel pins

Definition at line 105 of file SCMTriAssemblyMeshGenerator.h.

Referenced by buildPinMesh(), generate(), and SCMTriAssemblyMeshGenerator().

◆ _pin_block_id

const unsigned int SCMTriAssemblyMeshGenerator::_pin_block_id
protected

pin block index

Definition at line 39 of file SCMTriAssemblyMeshGenerator.h.

Referenced by buildPinMesh().

◆ _pin_diameter

const Real SCMTriAssemblyMeshGenerator::_pin_diameter
protected

fuel Pin diameter

Definition at line 61 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _pin_nodes

std::vector<std::vector<Node *> > SCMTriAssemblyMeshGenerator::_pin_nodes
protected

pin nodes

Definition at line 80 of file SCMTriAssemblyMeshGenerator.h.

Referenced by buildPinMesh(), and generate().

◆ _pin_position

std::vector<Point> SCMTriAssemblyMeshGenerator::_pin_position
protected

x,y coordinates of the fuel pins

Definition at line 97 of file SCMTriAssemblyMeshGenerator.h.

Referenced by buildPinMesh(), generate(), and SCMTriAssemblyMeshGenerator().

◆ _pin_to_chan_map

std::vector<std::vector<unsigned int> > SCMTriAssemblyMeshGenerator::_pin_to_chan_map
protected

stores the map from pins to channels

Definition at line 103 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _pins_in_rings

std::vector<std::vector<Real> > SCMTriAssemblyMeshGenerator::_pins_in_rings
protected

fuel pins that are belonging to each ring

Definition at line 99 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _pitch

const Real SCMTriAssemblyMeshGenerator::_pitch
protected

Distance between the neighbor fuel pins, pitch.

Definition at line 57 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _reduction_blockage

const std::vector<Real> SCMTriAssemblyMeshGenerator::_reduction_blockage
protected

area reduction of subchannels affected by blockage

Definition at line 53 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _sign_id_crossflow_map

std::vector<std::vector<Real> > SCMTriAssemblyMeshGenerator::_sign_id_crossflow_map
protected

Defines the global cross-flow direction -1 or 1 for each subchannel and for all gaps that are belonging to the corresponding subchannel.

Given a subchannel and a gap, if the neighbor subchannel index belonging to the same gap is lower, set it to -1, otherwise set it to 1.

Definition at line 91 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _spacer_k

const std::vector<Real>& SCMTriAssemblyMeshGenerator::_spacer_k
protected

form loss coefficient of the spacers

Definition at line 47 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _spacer_z

const std::vector<Real>& SCMTriAssemblyMeshGenerator::_spacer_z
protected

axial location of the spacers

Definition at line 45 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _subch_type

std::vector<EChannelType> SCMTriAssemblyMeshGenerator::_subch_type
protected

subchannel type

Definition at line 109 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _subchannel_block_id

const unsigned int SCMTriAssemblyMeshGenerator::_subchannel_block_id
protected

subchannel block index

Definition at line 37 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate().

◆ _subchannel_position

std::vector<std::vector<Real> > SCMTriAssemblyMeshGenerator::_subchannel_position
protected

x,y coordinates of the subchannel centroids

Definition at line 95 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _unheated_length_entry

const Real SCMTriAssemblyMeshGenerator::_unheated_length_entry
protected

unheated length of the fuel Pin at the entry of the assembly

Definition at line 31 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _unheated_length_exit

const Real SCMTriAssemblyMeshGenerator::_unheated_length_exit
protected

unheated length of the fuel Pin at the exit of the assembly

Definition at line 35 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _z_blockage

const std::vector<Real> SCMTriAssemblyMeshGenerator::_z_blockage
protected

axial location of blockage (inlet, outlet) [m]

Definition at line 49 of file SCMTriAssemblyMeshGenerator.h.

Referenced by generate(), and SCMTriAssemblyMeshGenerator().

◆ _z_grid

std::vector<Real> SCMTriAssemblyMeshGenerator::_z_grid
protected

axial location of nodes

Definition at line 41 of file SCMTriAssemblyMeshGenerator.h.

Referenced by buildPinMesh(), generate(), and SCMTriAssemblyMeshGenerator().


The documentation for this class was generated from the following files: