https://mooseframework.inl.gov
MultiAppSamplerControl.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 
10 // MOOSE includes
11 #include "MultiAppSamplerControl.h"
12 #include "Function.h"
13 #include "Sampler.h"
14 #include "MultiApp.h"
16 
17 registerMooseObject("StochasticToolsApp", MultiAppSamplerControl);
18 registerMooseObjectRenamed("StochasticToolsApp",
19  MultiAppCommandLineControl,
20  "01/01/2023 00:00",
22 
25 {
28  params.addClassDescription("Control for modifying the command line arguments of MultiApps.");
29 
30  // Set and suppress the 'execute_on' flag, it doesn't work with any other flag
31  params.set<ExecFlagEnum>("execute_on") = {EXEC_PRE_MULTIAPP_SETUP};
32  params.suppressParameter<ExecFlagEnum>("execute_on");
33 
34  params.addRequiredParam<MultiAppName>("multi_app", "The name of the MultiApp to control.");
35  params.addRequiredParam<SamplerName>(
36  "sampler",
37  "The Sampler object to utilize for altering the command line options of the MultiApp.");
38  params.addRequiredParam<std::vector<std::string>>(
39  "param_names", "The names of the command line parameters to set via the sampled data.");
40 
41  return params;
42 }
43 
45  : Control(parameters),
46  SamplerInterface(this),
47  _multi_app(_fe_problem.getMultiApp(getParam<MultiAppName>("multi_app"))),
48  _sampler(SamplerInterface::getSampler("sampler")),
49  _param_names(getParam<std::vector<std::string>>("param_names"))
50 {
53  "execute_on",
54  "The sampler object, '",
55  _sampler.name(),
56  "', is being used by the '",
57  name(),
58  "' object, thus the 'execute_on' of the sampler must include 'PRE_MULTIAPP_SETUP'.");
59 
60  if (_multi_app->usingPositions())
61  paramError("multi_app",
62  "The MultiApp must construct its sub-apps in initial setup but not during its "
63  "creation for '",
64  type(),
65  "'.\nTypically only sampler MultiApps work with '",
66  type(),
67  "' objects.");
68 
69  bool batch_reset = _multi_app->isParamValid("mode") &&
70  (_multi_app->getParam<MooseEnum>("mode") == "batch-reset");
71  bool batch_restore = _multi_app->isParamValid("mode") &&
72  (_multi_app->getParam<MooseEnum>("mode") == "batch-restore");
73  if (batch_reset)
74  ; // Do not perform the App count test, because in batch mode there is only one
75 
76  else if (batch_restore)
77  _multi_app->paramError(
78  "mode",
79  "The MultiApp object, '",
80  _multi_app->name(),
81  "', supplied to the '",
82  name(),
83  "' object is setup to run in 'batch-restore' mode, when using this mode command line "
84  "arguments cannot be modified; batch-reset mode should be used instead.");
85 
86  else if (_multi_app->numGlobalApps() != _sampler.getNumberOfRows())
87  mooseError("The number of sub apps (",
88  _multi_app->numGlobalApps(),
89  ") created by MultiApp object '",
90  _multi_app->name(),
91  "' must be equal to the number for rows (",
93  ") for the '",
94  _sampler.name(),
95  "' Sampler object.");
96 }
97 
98 void
100 {
101  // Do not put anything here, this method is being called after execute because the execute_on
102  // is set to PRE_MULTIAPP_SETUP for this class. It won't work any other way.
103 }
104 
105 void
107 {
108  // Gather the original arguments given in the parameter so we can keep them
109  if (_orig_args.empty())
110  {
111  _orig_args = getControllableValueByName<std::vector<CLIArgString>>(
112  "MultiApp", _multi_app->name(), "cli_args", true);
113  if (_orig_args.size() == 0)
114  _orig_args.push_back("");
115  else if (_param_names.size())
116  for (auto & clia : _orig_args)
117  clia += ";";
118  }
119 
120  auto cli_args = _orig_args;
121 
122  // To avoid storing duplicated param_names for each sampler, we store only param_names once in
123  // "cli_args".
124 
125  // Handle a couple errors up front regarding bracket expressions
126  bool has_brackets = false;
127  if (_param_names.size())
128  {
129  has_brackets = _param_names[0].find("[") != std::string::npos;
130  for (unsigned int i = 1; i < _param_names.size(); ++i)
131  if (has_brackets != (_param_names[i].find("[") != std::string::npos))
132  paramError("param_names",
133  "If the bracket is used, it must be provided to every parameter.");
134  }
135  if (!has_brackets && _sampler.getNumberOfCols() != _param_names.size())
136  paramError("param_names",
137  "The number of columns (",
139  ") must match the number of parameters (",
140  _param_names.size(),
141  ").");
142 
143  // Add the parameters that will be modified. The MultiApp will ultimately be
144  // responsible for assigning the values from the sampler.
145  std::ostringstream oss;
146  for (dof_id_type col = 0; col < _param_names.size(); ++col)
147  {
148  if (col > 0)
149  oss << ";";
150  oss << _param_names[col];
151  }
152 
153  // Put all the parameters in a single string
154  for (auto & clia : cli_args)
155  clia += oss.str();
156 
157  setControllableValueByName<std::vector<CLIArgString>>(
158  "MultiApp", _multi_app->name(), "cli_args", cli_args);
159 }
static InputParameters validParams()
static InputParameters validParams()
Sampler & _sampler
Sampler to utilize for creating MultiApps.
static InputParameters validParams()
A Control object for receiving data from a parent application Sampler object.
T & set(const std::string &name, bool quiet_mode=false)
virtual void initialSetup() override final
Do not allow the use of initialSetup, because this class is designed to operate on PRE_MULTIAPP_SETUP...
virtual const std::string & name() const
void addRequiredParam(const std::string &name, const std::string &doc_string)
void suppressParameter(const std::string &name)
MultiAppSamplerControl(const InputParameters &parameters)
const ExecFlagType EXEC_PRE_MULTIAPP_SETUP
std::vector< CLIArgString > _orig_args
The original cli_args from input.
const std::string & type() const
const T & getParam(const std::string &name) const
void paramError(const std::string &param, Args... args) const
bool isValueSet(const std::string &value) const
registerMooseObject("StochasticToolsApp", MultiAppSamplerControl)
dof_id_type getNumberOfRows() const
virtual void execute() override
void mooseError(Args &&... args) const
std::shared_ptr< MultiApp > _multi_app
The MultiApp this Transfer is transferring data to or from.
void addClassDescription(const std::string &doc_string)
const std::vector< std::string > & _param_names
Storage for the parameter names to be applied.
registerMooseObjectRenamed("StochasticToolsApp", MultiAppCommandLineControl, "01/01/2023 00:00", MultiAppSamplerControl)
dof_id_type getNumberOfCols() const
uint8_t dof_id_type