https://mooseframework.inl.gov
SubdomainExtraElementIDGenerator.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 
13 
14 #include "MooseMeshUtils.h"
15 
16 #include "libmesh/elem.h"
17 
20 {
22  params.addRequiredParam<MeshGeneratorName>(
23  "input", "Name of an existing mesh generator to which we assign element IDs");
24  params.addRequiredParam<std::vector<SubdomainName>>("subdomains",
25  "Subdomain names present in the input mesh");
26  params.addRequiredParam<std::vector<std::string>>("extra_element_id_names",
27  "List of user-defined extra element ID names");
28  params.addRequiredParam<std::vector<std::vector<dof_id_type>>>(
29  "extra_element_ids",
30  "User-defined extra element IDs corresponding to 'subdomains' in the same order");
31 
32  params.addParam<std::vector<dof_id_type>>(
33  "default_extra_element_ids", "Default extra element IDs for elements not in 'subdomains'");
34 
35  params.addClassDescription(
36  "Assign extra element IDs for elements on a mesh based on mesh subdomains.");
37  return params;
38 }
39 
41  : MeshGenerator(params),
42  _input(getMesh("input")),
43  _subdomain_names(getParam<std::vector<SubdomainName>>("subdomains")),
44  _id_names(getParam<std::vector<std::string>>("extra_element_id_names")),
45  _ids(getParam<std::vector<std::vector<dof_id_type>>>("extra_element_ids")),
46  _defaults(queryParam<std::vector<dof_id_type>>("default_extra_element_ids"))
47 {
48  if (_subdomain_names.size() == 0)
49  paramError("subdomains", "Empty subdomain vector provided!");
50  if (_id_names.size() != _ids.size())
51  paramError("extra_element_ids",
52  "Inconsistent vector size for element IDs (must have same size as "
53  "'extra_element_id_names')");
54  for (const auto i : index_range(_ids))
55  if (_subdomain_names.size() != _ids[i].size())
56  paramError("extra_element_ids",
57  "Inconsistent vector size for element IDs at index " + std::to_string(i) +
58  " (must have same size as 'subdomains')");
59  if (_defaults && _defaults->size() != _id_names.size())
60  paramError("default_extra_element_ids",
61  "Inconsistent vector size for default element IDs (must have same size as "
62  "'extra_element_id_names')");
63 }
64 
65 std::unique_ptr<MeshBase>
67 {
68  std::unique_ptr<MeshBase> mesh = std::move(_input);
69 
70  // We'll be querying the mesh for subdomain ids
71  if (!mesh->preparation().has_cached_elem_data)
72  mesh->cache_elem_data();
73 
74  // construct a map from the subdomain ID to the index in 'subdomains'
75  const auto subdomain_ids = MooseMeshUtils::getSubdomainIDs(*mesh, _subdomain_names);
76 
77  // check that all subdomains are present
78  for (const auto & name : _subdomain_names)
80  paramError("subdomains", "Subdomain " + name + " does not exist in the mesh");
81 
82  // check to make sure no duplicated subdomain ids
83  std::set<SubdomainID> unique_subdomain_ids;
84  for (const auto & id : subdomain_ids)
85  if (unique_subdomain_ids.count(id) > 0)
86  paramError("subdomains", "Cannot have subdomain with ID ", id, " listed more than once!");
87  else
88  unique_subdomain_ids.insert(id);
89 
90  std::map<SubdomainID, unsigned int> subdomains;
91  for (const auto i : index_range(_subdomain_names))
92  subdomains[subdomain_ids[i]] = i;
93 
94  // get indices for all extra element integers
95  std::vector<unsigned int> extra_id_indices;
96  for (const auto & id_name : _id_names)
97  {
98  if (!mesh->has_elem_integer(id_name))
99  extra_id_indices.push_back(mesh->add_elem_integer(id_name));
100  else
101  extra_id_indices.push_back(mesh->get_elem_integer_index(id_name));
102  }
103 
104  for (auto & elem : mesh->element_ptr_range())
105  {
106  if (const auto it = subdomains.find(elem->subdomain_id()); it != subdomains.end())
107  {
108  for (const auto i : index_range(_ids))
109  elem->set_extra_integer(extra_id_indices[i], _ids[i][it->second]);
110  }
111  else if (_defaults)
112  {
113  for (const auto i : index_range(_ids))
114  elem->set_extra_integer(extra_id_indices[i], (*_defaults)[i]);
115  }
116  }
117 
118  return mesh;
119 }
void paramError(const std::string &param, Args... args) const
T & getMesh(MooseMesh &mesh)
function to cast mesh
Definition: SCM.h:35
void addParam(const std::string &name, const std::initializer_list< typename T::value_type > &value, const std::string &doc_string)
SubdomainExtraElementIDGenerator(const InputParameters &parameters)
MeshBase & mesh
std::vector< subdomain_id_type > getSubdomainIDs(const libMesh::MeshBase &mesh, const std::vector< SubdomainName > &subdomain_name)
void addRequiredParam(const std::string &name, const std::string &doc_string)
virtual std::unique_ptr< MeshBase > generate() override
const std::vector< SubdomainName > & _subdomain_names
subdomains that are to be assigned with element IDs
const std::string & name() const
registerMooseObject("ReactorApp", SubdomainExtraElementIDGenerator)
const std::vector< std::string > & _id_names
The names for each ID from input.
std::unique_ptr< MeshBase > & _input
input mesh for adding element IDs
static InputParameters validParams()
const std::vector< dof_id_type > *const _defaults
The default IDs from input, if any.
bool hasSubdomainName(const MeshBase &input_mesh, const SubdomainName &name)
const std::vector< std::vector< dof_id_type > > & _ids
The IDs from input.
void addClassDescription(const std::string &doc_string)
auto index_range(const T &sizable)
uint8_t dof_id_type