Tempus  Version of the Day
Time Integration
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Pages
Tempus_StaggeredForwardSensitivityModelEvaluator_impl.hpp
Go to the documentation of this file.
1 // @HEADER
2 // ****************************************************************************
3 // Tempus: Copyright (2017) Sandia Corporation
4 //
5 // Distributed under BSD 3-clause license (See accompanying file Copyright.txt)
6 // ****************************************************************************
7 // @HEADER
8 
9 #ifndef Tempus_StaggeredForwardSensitivityModelEvaluator_impl_hpp
10 #define Tempus_StaggeredForwardSensitivityModelEvaluator_impl_hpp
11 
12 #include "Thyra_DefaultMultiVectorProductVector.hpp"
16 #include "Thyra_VectorStdOps.hpp"
17 #include "Thyra_MultiVectorStdOps.hpp"
18 
19 namespace Tempus {
20 
21 template <typename Scalar>
24  const Teuchos::RCP<const Thyra::ModelEvaluator<Scalar> > & model,
25  const Teuchos::RCP<const Teuchos::ParameterList>& pList,
26  const Teuchos::RCP<MultiVector>& dxdp_init,
27  const Teuchos::RCP<MultiVector>& dx_dotdp_init,
28  const Teuchos::RCP<MultiVector>& dx_dotdotdp_init) :
29  model_(model),
30  dxdp_init_(dxdp_init),
31  dx_dotdp_init_(dx_dotdp_init),
32  dx_dotdotdp_init_(dx_dotdotdp_init),
33  p_index_(0),
34  x_tangent_index_(1),
35  xdot_tangent_index_(2),
36  xdotdot_tangent_index_(3),
37  use_dfdp_as_tangent_(false),
38  t_interp_(Teuchos::ScalarTraits<Scalar>::rmax())
39 {
40  typedef Thyra::ModelEvaluatorBase MEB;
41 
42  // Set parameters
43  Teuchos::RCP<Teuchos::ParameterList> pl =
44  Teuchos::rcp(new Teuchos::ParameterList);
45  if (pList != Teuchos::null)
46  *pl = *pList;
47  pl->validateParametersAndSetDefaults(*this->getValidParameters());
48  use_dfdp_as_tangent_ = pl->get<bool>("Use DfDp as Tangent");
49  p_index_ = pl->get<int>("Sensitivity Parameter Index");
50  x_tangent_index_ = pl->get<int>("Sensitivity X Tangent Index");
51  xdot_tangent_index_ = pl->get<int>("Sensitivity X-Dot Tangent Index");
52  xdotdot_tangent_index_ = pl->get<int>("Sensitivity X-Dot-Dot Tangent Index");
53 
54  num_param_ = model_->get_p_space(p_index_)->dim();
55  dxdp_space_ =
56  Thyra::multiVectorProductVectorSpace(model_->get_x_space(), num_param_);
57  dfdp_space_ =
58  Thyra::multiVectorProductVectorSpace(model_->get_f_space(), num_param_);
59 
60  MEB::InArgs<Scalar> me_inArgs = model_->createInArgs();
61  MEB::InArgsSetup<Scalar> inArgs;
62  inArgs.setModelEvalDescription(this->description());
63  inArgs.setSupports(MEB::IN_ARG_x);
64  if (me_inArgs.supports(MEB::IN_ARG_x_dot))
65  inArgs.setSupports(MEB::IN_ARG_x_dot);
66  if (me_inArgs.supports(MEB::IN_ARG_t))
67  inArgs.setSupports(MEB::IN_ARG_t);
68  if (me_inArgs.supports(MEB::IN_ARG_alpha))
69  inArgs.setSupports(MEB::IN_ARG_alpha);
70  if (me_inArgs.supports(MEB::IN_ARG_beta))
71  inArgs.setSupports(MEB::IN_ARG_beta);
72  if (me_inArgs.supports(MEB::IN_ARG_W_x_dot_dot_coeff))
73  inArgs.setSupports(MEB::IN_ARG_W_x_dot_dot_coeff);
74 
75  // Support additional parameters for x and xdot
76  inArgs.set_Np(me_inArgs.Np());
77  prototypeInArgs_ = inArgs;
78 
79  MEB::OutArgs<Scalar> me_outArgs = model_->createOutArgs();
80  MEB::OutArgsSetup<Scalar> outArgs;
81  outArgs.setModelEvalDescription(this->description());
82  outArgs.set_Np_Ng(me_inArgs.Np(),me_outArgs.Ng());
83  outArgs.setSupports(MEB::OUT_ARG_f);
84  outArgs.setSupports(MEB::OUT_ARG_W_op);
85  for (int j=0; j<me_outArgs.Ng(); ++j) {
86  outArgs.setSupports(MEB::OUT_ARG_DgDx_dot, j,
87  me_outArgs.supports(MEB::OUT_ARG_DgDx_dot, j));
88  outArgs.setSupports(MEB::OUT_ARG_DgDx, j,
89  me_outArgs.supports(MEB::OUT_ARG_DgDx, j));
90  for (int l=0; l<me_outArgs.Np(); ++l) {
91  outArgs.setSupports(MEB::OUT_ARG_DgDp, j, l,
92  me_outArgs.supports(MEB::OUT_ARG_DgDp, j, l));
93  }
94  }
95  prototypeOutArgs_ = outArgs;
96 
97  TEUCHOS_ASSERT(me_outArgs.supports(MEB::OUT_ARG_DfDp, p_index_).supports(MEB::DERIV_MV_JACOBIAN_FORM));
99  TEUCHOS_ASSERT(me_outArgs.supports(MEB::OUT_ARG_W_op));
100 }
101 
102 template <typename Scalar>
103 void
106  const Teuchos::RCP<const Tempus::SolutionHistory<Scalar> >& sh)
107 {
108  sh_ = sh;
109  t_interp_ = Teuchos::ScalarTraits<Scalar>::rmax();
110 }
111 
112 template <typename Scalar>
113 void
116  const Teuchos::RCP<const Tempus::SolutionState<Scalar> >& s)
117 {
118  sh_ = Teuchos::null;
119  forward_state_ = s;
120 }
121 
122 template <typename Scalar>
123 Teuchos::RCP<const Thyra::VectorSpaceBase<Scalar> >
125 get_p_space(int p) const
126 {
127  TEUCHOS_ASSERT(p < model_->Np());
128  return model_->get_p_space(p);
129 }
130 
131 template <typename Scalar>
132 Teuchos::RCP<const Teuchos::Array<std::string> >
134 get_p_names(int p) const
135 {
136  TEUCHOS_ASSERT(p < model_->Np());
137  return model_->get_p_names(p);
138 }
139 
140 template <typename Scalar>
141 Teuchos::RCP<const Thyra::VectorSpaceBase<Scalar> >
143 get_x_space() const
144 {
145  return dxdp_space_;
146 }
147 
148 template <typename Scalar>
149 Teuchos::RCP<const Thyra::VectorSpaceBase<Scalar> >
151 get_f_space() const
152 {
153  return dfdp_space_;
154 }
155 
156 template <typename Scalar>
157 Teuchos::RCP<const Thyra::VectorSpaceBase<Scalar> >
159 get_g_space(int j) const
160 {
161  return model_->get_g_space(j);
162 }
163 
164 template <typename Scalar>
165 Teuchos::ArrayView<const std::string>
167 get_g_names(int j) const
168 {
169  return model_->get_g_names(j);
170 }
171 
172 template <typename Scalar>
173 Teuchos::RCP<Thyra::LinearOpBase<Scalar> >
175 create_W_op() const
176 {
177  Teuchos::RCP<Thyra::LinearOpBase<Scalar> > op;
178  if (lo_ != Teuchos::null)
179  op = lo_;
180  else
181  op = model_->create_W_op();
182  return Thyra::nonconstMultiVectorLinearOp(op, num_param_);
183 }
184 
185 template <typename Scalar>
186 Teuchos::RCP<Thyra::LinearOpBase<Scalar> >
188 create_DgDx_dot_op(int j) const
189 {
190  return model_->create_DgDx_dot_op(j);
191 }
192 
193 template <typename Scalar>
194 Teuchos::RCP<Thyra::LinearOpBase<Scalar> >
196 create_DgDx_op(int j) const
197 {
198  return model_->create_DgDx_op(j);
199 }
200 
201 template <typename Scalar>
202 Teuchos::RCP<Thyra::LinearOpBase<Scalar> >
204 create_DgDp_op(int j, int l) const
205 {
206  return model_->create_DgDp_op(j,l);
207 }
208 
209 template <typename Scalar>
210 Teuchos::RCP<const Thyra::LinearOpWithSolveFactoryBase<Scalar> >
213 {
214  using Teuchos::RCP;
215  using Teuchos::rcp_dynamic_cast;
216 
217  Teuchos::RCP<const Thyra::LinearOpWithSolveFactoryBase<Scalar> > factory;
218  Teuchos::RCP<const Thyra::LinearOpWithSolveFactoryBase<Scalar> > model_factory
219  = model_->get_W_factory();
220  if (model_factory == Teuchos::null)
221  return Teuchos::null; // model_ doesn't support W_factory
222  if (po_ != Teuchos::null) {
223  factory =
224  Thyra::reuseLinearOpWithSolveFactory<Scalar>(model_factory, po_);
225  }
226  else
227  factory = model_factory;
228  return Thyra::multiVectorLinearOpWithSolveFactory(factory,
229  dfdp_space_,
230  dxdp_space_);
231 }
232 
233 template <typename Scalar>
234 Thyra::ModelEvaluatorBase::InArgs<Scalar>
237 {
238  return prototypeInArgs_;
239 }
240 
241 template <typename Scalar>
242 Thyra::ModelEvaluatorBase::InArgs<Scalar>
245 {
246  typedef Thyra::ModelEvaluatorBase MEB;
247  typedef Thyra::DefaultMultiVectorProductVector<Scalar> DMVPV;
248  using Teuchos::RCP;
249  using Teuchos::rcp_dynamic_cast;
250 
251  MEB::InArgs<Scalar> me_nominal = model_->getNominalValues();
252  MEB::InArgs<Scalar> nominal = this->createInArgs();
253 
254  const Scalar zero = Teuchos::ScalarTraits<Scalar>::zero();
255 
256  // Set initial x. If dxdp_init == null, set initial dx/dp = 0
257  RCP< Thyra::VectorBase<Scalar> > x = Thyra::createMember(*dxdp_space_);
258  RCP<DMVPV> dxdp = rcp_dynamic_cast<DMVPV>(x,true);
259  if (dxdp_init_ == Teuchos::null)
260  Thyra::assign(dxdp->getNonconstMultiVector().ptr(), zero);
261  else
262  Thyra::assign(dxdp->getNonconstMultiVector().ptr(), *dxdp_init_);
263  nominal.set_x(x);
264 
265  // Set initial xdot. If dx_dotdp_init == null, set initial dxdot/dp = 0
266  if (me_nominal.supports(MEB::IN_ARG_x_dot)) {
267  RCP< Thyra::VectorBase<Scalar> > xdot = Thyra::createMember(*dxdp_space_);
268  RCP<DMVPV> dxdotdp = rcp_dynamic_cast<DMVPV>(xdot,true);
269  if (dx_dotdp_init_ == Teuchos::null)
270  Thyra::assign(dxdotdp->getNonconstMultiVector().ptr(), zero);
271  else
272  Thyra::assign(dxdotdp->getNonconstMultiVector().ptr(), *dx_dotdp_init_);
273  nominal.set_x_dot(xdot);
274  }
275 
276  // Set initial xdotdot. If dx_dotdotdp_init == null, set initial dxdotdot/dp = 0
277  if (me_nominal.supports(MEB::IN_ARG_x_dot_dot)) {
278  RCP< Thyra::VectorBase<Scalar> > xdotdot =
279  Thyra::createMember(*dxdp_space_);
280  RCP<DMVPV> dxdotdotdp = rcp_dynamic_cast<DMVPV>(xdotdot,true);
281  if (dx_dotdotdp_init_ == Teuchos::null)
282  Thyra::assign(dxdotdotdp->getNonconstMultiVector().ptr(), zero);
283  else
284  Thyra::assign(dxdotdotdp->getNonconstMultiVector().ptr(),
285  *dx_dotdotdp_init_);
286  nominal.set_x_dot_dot(xdotdot);
287  }
288 
289  const int np = model_->Np();
290  for (int i=0; i<np; ++i)
291  nominal.set_p(i, me_nominal.get_p(i));
292  return nominal;
293 }
294 
295 template <typename Scalar>
296 Thyra::ModelEvaluatorBase::OutArgs<Scalar>
299 {
300  return prototypeOutArgs_;
301 }
302 
303 template <typename Scalar>
304 void
306 evalModelImpl(const Thyra::ModelEvaluatorBase::InArgs<Scalar> &inArgs,
307  const Thyra::ModelEvaluatorBase::OutArgs<Scalar> &outArgs) const
308 {
309  typedef Thyra::ModelEvaluatorBase MEB;
310  typedef Thyra::DefaultMultiVectorProductVector<Scalar> DMVPV;
311  using Teuchos::RCP;
312  using Teuchos::rcp_dynamic_cast;
313 
314  // Interpolate forward solution at supplied time, reusing previous
315  // interpolation if possible
316  Scalar forward_t;
317  if (sh_ != Teuchos::null) {
318  forward_t = inArgs.get_t();
319  if (t_interp_ != forward_t) {
320  if (nc_forward_state_ == Teuchos::null)
321  nc_forward_state_ = sh_->interpolateState(forward_t);
322  else
323  sh_->interpolateState(forward_t, nc_forward_state_.get());
324  forward_state_ = nc_forward_state_;
325  t_interp_ = forward_t;
326  }
327  }
328  else {
329  TEUCHOS_ASSERT(forward_state_ != Teuchos::null);
330  forward_t = forward_state_->getTime();
331  }
332 
333  // setup input arguments for model
334  RCP< const Thyra::MultiVectorBase<Scalar> > dxdp, dxdotdp, dxdotdotdp;
335  MEB::InArgs<Scalar> me_inArgs = model_->getNominalValues();
336  dxdp = rcp_dynamic_cast<const DMVPV>(inArgs.get_x(),true)->getMultiVector();
337  me_inArgs.set_x(forward_state_->getX());
338  if (use_dfdp_as_tangent_)
339  me_inArgs.set_p(x_tangent_index_, inArgs.get_x());
340  if (me_inArgs.supports(MEB::IN_ARG_x_dot)) {
341  if (inArgs.get_x_dot() != Teuchos::null) {
342  dxdotdp =
343  rcp_dynamic_cast<const DMVPV>(inArgs.get_x_dot(),true)->getMultiVector();
344  me_inArgs.set_x_dot(forward_state_->getXDot());
345  if (use_dfdp_as_tangent_)
346  me_inArgs.set_p(xdot_tangent_index_, inArgs.get_x_dot());
347  }
348  else {
349  // clear out xdot if it was set in nominalValues to get to ensure we
350  // get the explicit form
351  me_inArgs.set_x_dot(Teuchos::null);
352  }
353  }
354  if (me_inArgs.supports(MEB::IN_ARG_x_dot_dot)) {
355  if (inArgs.get_x_dot_dot() != Teuchos::null) {
356  dxdotdotdp =
357  rcp_dynamic_cast<const DMVPV>(inArgs.get_x_dot_dot(),true)->getMultiVector();
358  me_inArgs.set_x_dot_dot(forward_state_->getXDotDot());
359  if (use_dfdp_as_tangent_)
360  me_inArgs.set_p(xdotdot_tangent_index_, inArgs.get_x_dot_dot());
361  }
362  else // clear out xdotdot if it was set in nominalValues
363  me_inArgs.set_x_dot_dot(Teuchos::null);
364  }
365  if (me_inArgs.supports(MEB::IN_ARG_t))
366  me_inArgs.set_t(forward_t);
367  if (me_inArgs.supports(MEB::IN_ARG_alpha))
368  me_inArgs.set_alpha(inArgs.get_alpha());
369  if (me_inArgs.supports(MEB::IN_ARG_beta))
370  me_inArgs.set_beta(inArgs.get_beta());
371  if (me_inArgs.supports(MEB::IN_ARG_W_x_dot_dot_coeff))
372  me_inArgs.set_W_x_dot_dot_coeff(inArgs.get_W_x_dot_dot_coeff());
373 
374  // Set parameters -- be careful to only set ones that were set in our
375  // inArgs to not null out any specified through nominalValues or
376  // dx/dp above
377  const int np = me_inArgs.Np();
378  for (int i=0; i<np; ++i) {
379  if (inArgs.get_p(i) != Teuchos::null)
380  if (!use_dfdp_as_tangent_ ||
381  (use_dfdp_as_tangent_ && i != x_tangent_index_ &&
382  i != xdot_tangent_index_ &&
383  i != xdotdot_tangent_index_ ))
384  me_inArgs.set_p(i, inArgs.get_p(i));
385  }
386 
387  // setup output arguments for model
388  RCP< Thyra::MultiVectorBase<Scalar> > dfdp;
389  MEB::OutArgs<Scalar> me_outArgs = model_->createOutArgs();
390  if (outArgs.get_f() != Teuchos::null) {
391  dfdp = rcp_dynamic_cast<DMVPV>(outArgs.get_f(),true)->getNonconstMultiVector();
392  me_outArgs.set_DfDp(p_index_, dfdp);
393  }
394  if (lo_ == Teuchos::null && outArgs.get_W_op() != Teuchos::null) {
395  RCP<Thyra::LinearOpBase<Scalar> > op = outArgs.get_W_op();
396  RCP<Thyra::MultiVectorLinearOp<Scalar> > mv_op =
397  rcp_dynamic_cast<Thyra::MultiVectorLinearOp<Scalar> >(op,true);
398  me_outArgs.set_W_op(mv_op->getNonconstLinearOp());
399  }
400  for (int j=0; j<outArgs.Ng(); ++j) {
401  if (!me_outArgs.supports(MEB::OUT_ARG_DgDx_dot,j).none())
402  me_outArgs.set_DgDx_dot(j, outArgs.get_DgDx_dot(j));
403  if (!me_outArgs.supports(MEB::OUT_ARG_DgDx,j).none())
404  me_outArgs.set_DgDx(j, outArgs.get_DgDx(j));
405  for (int l=0; l<outArgs.Np(); ++l)
406  if (!me_outArgs.supports(MEB::OUT_ARG_DgDp,j,l).none())
407  me_outArgs.set_DgDp(j, l, outArgs.get_DgDp(j,l));
408  }
409 
410  // build residual and jacobian
411  model_->evalModel(me_inArgs, me_outArgs);
412 
413  // Compute (df/dx) * (dx/dp) + (df/dxdot) * (dxdot/dp) + (df/dxdotdot) * (dxdotdot/dp) + (df/dp)
414  // if the underlying ME doesn't already do this. This requires computing
415  // df/dx, df/dxdot, df/dxdotdot as separate operators.
416  // For pseudo-transient, we would like to reuse these operators, but this is
417  // complicated when steppers use both implicit and explicit forms.
418  if (!use_dfdp_as_tangent_) {
419  if (dxdp != Teuchos::null && dfdp != Teuchos::null) {
420  if (my_dfdx_ == Teuchos::null)
421  my_dfdx_ = model_->create_W_op();
422  MEB::OutArgs<Scalar> meo = model_->createOutArgs();
423  meo.set_W_op(my_dfdx_);
424  if (me_inArgs.supports(MEB::IN_ARG_alpha))
425  me_inArgs.set_alpha(0.0);
426  if (me_inArgs.supports(MEB::IN_ARG_beta))
427  me_inArgs.set_beta(1.0);
428  if (me_inArgs.supports(MEB::IN_ARG_W_x_dot_dot_coeff))
429  me_inArgs.set_W_x_dot_dot_coeff(0.0);
430  model_->evalModel(me_inArgs, meo);
431  my_dfdx_->apply(Thyra::NOTRANS, *dxdp, dfdp.ptr(), Scalar(1.0), Scalar(1.0));
432  }
433  if (dxdotdp != Teuchos::null && dfdp != Teuchos::null) {
434  if (my_dfdxdot_ == Teuchos::null)
435  my_dfdxdot_ = model_->create_W_op();
436  MEB::OutArgs<Scalar> meo = model_->createOutArgs();
437  meo.set_W_op(my_dfdxdot_);
438  if (me_inArgs.supports(MEB::IN_ARG_alpha))
439  me_inArgs.set_alpha(1.0);
440  if (me_inArgs.supports(MEB::IN_ARG_beta))
441  me_inArgs.set_beta(0.0);
442  if (me_inArgs.supports(MEB::IN_ARG_W_x_dot_dot_coeff))
443  me_inArgs.set_W_x_dot_dot_coeff(0.0);
444  model_->evalModel(me_inArgs, meo);
445  my_dfdxdot_->apply(Thyra::NOTRANS, *dxdotdp, dfdp.ptr(), Scalar(1.0), Scalar(1.0));
446  }
447  if (dxdotdotdp != Teuchos::null && dfdp != Teuchos::null) {
448  if (my_dfdxdotdot_ == Teuchos::null)
449  my_dfdxdotdot_ = model_->create_W_op();
450  MEB::OutArgs<Scalar> meo = model_->createOutArgs();
451  meo.set_W_op(my_dfdxdotdot_);
452  if (me_inArgs.supports(MEB::IN_ARG_alpha))
453  me_inArgs.set_alpha(0.0);
454  if (me_inArgs.supports(MEB::IN_ARG_beta))
455  me_inArgs.set_beta(0.0);
456  if (me_inArgs.supports(MEB::IN_ARG_W_x_dot_dot_coeff))
457  me_inArgs.set_W_x_dot_dot_coeff(1.0);
458  model_->evalModel(me_inArgs, meo);
459  my_dfdxdotdot_->apply(Thyra::NOTRANS, *dxdotdotdp, dfdp.ptr(), Scalar(1.0), Scalar(1.0));
460  }
461  }
462 }
463 
464 template<class Scalar>
465 Teuchos::RCP<const Teuchos::ParameterList>
468 {
469  Teuchos::RCP<Teuchos::ParameterList> pl = Teuchos::parameterList();
470  pl->set<bool>("Use DfDp as Tangent", false);
471  pl->set<int>("Sensitivity Parameter Index", 0);
472  pl->set<int>("Sensitivity X Tangent Index", 1);
473  pl->set<int>("Sensitivity X-Dot Tangent Index", 2);
474  pl->set<int>("Sensitivity X-Dot-Dot Tangent Index", 3);
475  return pl;
476 }
477 
478 } // namespace Tempus
479 
480 #endif
void setForwardSolutionHistory(const Teuchos::RCP< const Tempus::SolutionHistory< Scalar > > &sh)
Set solution history from forward state evaluation (for interpolation)
virtual void setForwardSolutionState(const Teuchos::RCP< const Tempus::SolutionState< Scalar > > &s)
Set solution state from forward state evaluation (for frozen state)
Teuchos::RCP< const Teuchos::Array< std::string > > get_p_names(int p) const
Teuchos::RCP< const Thyra::DefaultMultiVectorProductVectorSpace< Scalar > > dxdp_space_
Teuchos::RCP< const Thyra::VectorSpaceBase< Scalar > > get_p_space(int p) const
StaggeredForwardSensitivityModelEvaluator(const Teuchos::RCP< const Thyra::ModelEvaluator< Scalar > > &model, const Teuchos::RCP< const Teuchos::ParameterList > &pList=Teuchos::null, const Teuchos::RCP< MultiVector > &dxdp_init=Teuchos::null, const Teuchos::RCP< MultiVector > &dx_dotdp_init=Teuchos::null, const Teuchos::RCP< MultiVector > &dx_dotdot_dp_init=Teuchos::null)
Constructor.
Teuchos::RCP< Thyra::LinearOpBase< Scalar > > create_DgDx_dot_op(int j) const
Teuchos::RCP< const Thyra::DefaultMultiVectorProductVectorSpace< Scalar > > dfdp_space_
SolutionHistory is basically a container of SolutionStates. SolutionHistory maintains a collection of...
Teuchos::RCP< Thyra::LinearOpBase< Scalar > > create_DgDp_op(int j, int l) const
Teuchos::RCP< const Thyra::VectorSpaceBase< Scalar > > get_x_space() const
Implicit concrete LinearOpBase subclass that takes a flattended out multi-vector and performs a multi...
Teuchos::RCP< const Thyra::LinearOpWithSolveFactoryBase< Scalar > > get_W_factory() const
Teuchos::RCP< Thyra::LinearOpBase< Scalar > > create_DgDx_op(int j) const
Teuchos::RCP< const Thyra::VectorSpaceBase< Scalar > > get_f_space() const
Solution state for integrators and steppers. SolutionState contains the metadata for solutions and th...
Teuchos::RCP< const Thyra::VectorSpaceBase< Scalar > > get_g_space(int j) const
void evalModelImpl(const Thyra::ModelEvaluatorBase::InArgs< Scalar > &inArgs, const Thyra::ModelEvaluatorBase::OutArgs< Scalar > &outArgs) const