https://mooseframework.inl.gov
Loading...
Searching...
No Matches
NestedSolve.h
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#pragma once
11
12#include "MooseTypes.h"
13#include "RankTwoTensor.h"
14#include "InputParameters.h"
15
16#include "libmesh/utility.h"
17#include "libmesh/int_range.h"
18#include "libmesh/vector_value.h"
19
20#include "Eigen/Core"
21#include <Eigen/Dense>
22#include <unsupported/Eigen/NonLinearOptimization>
23
24#include "EigenADReal.h"
25
31{
32template <typename T>
34}
35
41template <bool is_ad>
43{
44public:
46
48 NestedSolveTempl(const InputParameters & params);
49
55
57 using DynamicVector = Eigen::Matrix<NSReal, Eigen::Dynamic, 1>;
58 using DynamicMatrix = Eigen::Matrix<NSReal, Eigen::Dynamic, Eigen::Dynamic>;
60
62 template <typename T>
64 template <typename T>
67
69 template <int N = 0>
70 using Value =
71 typename std::conditional<N == 1,
72 NSReal,
73 typename std::conditional<N == 0,
75 Eigen::Matrix<NSReal, N, 1>>::type>::type;
76
78 template <int N = 0>
79 using Jacobian =
80 typename std::conditional<N == 1,
81 NSReal,
82 typename std::conditional<N == 0,
84 Eigen::Matrix<NSReal, N, N>>::type>::type;
85
87 template <typename V, typename T>
88 void nonlinear(V & guess, T && compute);
89
91 template <typename V, typename T, typename C>
92 void nonlinearDamped(V & guess, T && compute, C && computeCondition);
93
96 template <typename R, typename J>
97 void nonlinear(DynamicVector & guess, R & computeResidual, J & computeJacobian);
98 template <typename R, typename J>
99 void nonlinear(NSReal & guess, R & computeResidual, J & computeJacobian);
100 template <typename R, typename J>
101 void nonlinear(NSRealVectorValue & guess, R & computeResidual, J & computeJacobian);
103
106 template <typename R, typename J>
107 void nonlinearTight(DynamicVector & guess, R & computeResidual, J & computeJacobian);
108 template <typename R, typename J>
109 void nonlinearTight(NSReal & guess, R & computeResidual, J & computeJacobian);
110 template <typename R, typename J>
111 void nonlinearTight(NSRealVectorValue & guess, R & computeResidual, J & computeJacobian);
113
115 template <typename R, typename J, typename B>
116 void
117 nonlinearBounded(NSReal & guess, R & computeResidual, J & computeJacobian, B & computeBounds);
120 static Real relativeToleranceDefault() { return 1e-8; }
121 static Real absoluteToleranceDefault() { return 1e-13; }
122 static Real xToleranceDefault() { return 1e-15; }
123 static unsigned int minIterationsDefault() { return 3; }
124 static unsigned int maxIterationsDefault() { return 1000; }
125 static Real acceptableMultiplierDefault() { return 10.0; }
126 static Real dampingFactorDefault() { return 0.8; }
127 static unsigned int maxDampingIterationsDefault() { return 100; }
129
130 void setRelativeTolerance(Real rel) { _relative_tolerance_square = rel * rel; }
131 void setAbsoluteTolerance(Real abs) { _absolute_tolerance_square = abs * abs; }
133
141
142 unsigned int _min_iterations;
143 unsigned int _max_iterations;
145
159
161 const State & getState() const { return _state; }
163 const std::size_t & getIterations() { return _n_iterations; };
164
166 template <typename V>
167 static Real normSquare(const V & v);
168 static Real normSquare(const NSReal & v);
169 static Real normSquare(const NSRealVectorValue & v);
171
173 //'b' by a factor of 'c'
174 template <typename V>
175 static bool isRelSmall(const V & a, const V & b, const V & c);
176 static bool isRelSmall(const NSReal & a, const NSReal & b, const NSReal & c);
177 static bool
178 isRelSmall(const NSRealVectorValue & a, const NSRealVectorValue & b, const NSReal & c);
179 static bool isRelSmall(const DynamicVector & a, const DynamicVector & b, const NSReal & c);
181
182protected:
185
187 std::size_t _n_iterations;
188
193
195 template <typename V, typename T>
196 void sizeItems(const V &, V &, T &) const
197 {
198 }
199
201 template <typename J, typename V>
202 void linear(const J & A, V & x, const V & b) const;
203 void linear(const NSReal & A, NSReal & x, const NSReal & b) const { x = b / A; }
204 void linear(const NSRankTwoTensor & A, NSRealVectorValue & x, const NSRealVectorValue & b) const;
206
208 bool isConverged(Real r0_square, Real r_square, bool acceptable);
209
210private:
212 template <bool store_residual_norm, typename R, typename J>
213 auto make_adaptor(R & residual, J & jacobian);
214 template <bool store_residual_norm, typename R, typename J>
215 auto make_real_adaptor(R & residual, J & jacobian);
216 template <bool store_residual_norm, typename R, typename J>
217 auto make_realvector_adaptor(R & residual, J & jacobian);
219};
220
221template <bool is_ad>
222template <typename R, typename J>
223void
225 R & computeResidual,
226 J & computeJacobian)
227{
228 // adaptor functor to utilize the Eigen non-linear solver
229 auto functor = make_adaptor<true>(computeResidual, computeJacobian);
230 Eigen::HybridNonLinearSolver<decltype(functor), NSReal> solver(functor);
231 auto status = solver.solve(guess);
232
233 if (status == Eigen::HybridNonLinearSolverSpace::RelativeErrorTooSmall)
234 _state = State::CONVERGED_REL;
235 else
236 _state = State::NOT_CONVERGED;
237}
238
239template <bool is_ad>
240template <typename R, typename J>
241void
242NestedSolveTempl<is_ad>::nonlinear(NSReal & guess, R & computeResidual, J & computeJacobian)
243{
245
246 // adaptor functor to utilize the Eigen non-linear solver
247 auto functor = make_real_adaptor<true>(computeResidual, computeJacobian);
248 Eigen::HybridNonLinearSolver<decltype(functor), NSReal> solver(functor);
249 V guess_eigen(1);
250 guess_eigen << guess;
251 const auto & r_square = functor.getResidualNorm();
252 solver.solveInit(guess_eigen);
253
254 // compute first residual norm for relative convergence checks
255 auto r0_square = r_square;
256 if (r0_square == 0)
257 {
258 _state = State::EXACT_GUESS;
259 return;
260 }
261
262 // perform non-linear iterations
263 _n_iterations = 1;
264 while (_n_iterations <= _max_iterations &&
265 solver.solveOneStep(guess_eigen) == Eigen::HybridNonLinearSolverSpace::Running)
266 {
267 // check convergence
268 if (_n_iterations >= _min_iterations && isConverged(r0_square, r_square, /*acceptable=*/false))
269 {
270 guess = guess_eigen(0);
271 return;
272 }
273 _n_iterations++;
274 }
275
279 if (!isConverged(r0_square, r_square, /*acceptable=*/true))
280 _state = State::NOT_CONVERGED;
281
282 guess = guess_eigen(0);
283}
284
285template <bool is_ad>
286template <typename R, typename J>
287void
289 R & computeResidual,
290 J & computeJacobian)
291{
293
294 // adaptor functor to utilize the Eigen non-linear solver
295 auto functor = make_realvector_adaptor<true>(computeResidual, computeJacobian);
296 Eigen::HybridNonLinearSolver<decltype(functor), NSReal> solver(functor);
297 V guess_eigen(3);
298 guess_eigen << guess(0), guess(1), guess(2);
299 auto status = solver.solve(guess_eigen);
300 guess(0) = guess_eigen(0);
301 guess(1) = guess_eigen(1);
302 guess(2) = guess_eigen(2);
303
304 if (status == Eigen::HybridNonLinearSolverSpace::RelativeErrorTooSmall)
305 _state = State::CONVERGED_REL;
306 else
307 _state = State::NOT_CONVERGED;
308}
309
310template <bool is_ad>
311template <typename R, typename J>
312void
314 R & computeResidual,
315 J & computeJacobian)
316{
317 // adaptor functor to utilize the Eigen non-linear solver
318 auto functor = make_adaptor<false>(computeResidual, computeJacobian);
319 Eigen::HybridNonLinearSolver<decltype(functor), NSReal> solver(functor);
320 auto status = solver.solve(guess);
321
322 if (status == Eigen::HybridNonLinearSolverSpace::RelativeErrorTooSmall)
323 _state = State::CONVERGED_REL;
324 else
325 _state = State::NOT_CONVERGED;
326}
327
328template <bool is_ad>
329template <typename R, typename J>
330void
331NestedSolveTempl<is_ad>::nonlinearTight(NSReal & guess, R & computeResidual, J & computeJacobian)
332{
334
335 // adaptor functor to utilize the Eigen non-linear solver
336 auto functor = make_real_adaptor<false>(computeResidual, computeJacobian);
337 Eigen::HybridNonLinearSolver<decltype(functor), NSReal> solver(functor);
338 V guess_eigen(1);
339 guess_eigen << guess;
340 auto status = solver.solve(guess_eigen);
341 guess = guess_eigen(0);
342
343 if (status == Eigen::HybridNonLinearSolverSpace::RelativeErrorTooSmall)
344 _state = State::CONVERGED_REL;
345 else
346 _state = State::NOT_CONVERGED;
347}
348
349template <bool is_ad>
350template <typename R, typename J>
351void
353 R & computeResidual,
354 J & computeJacobian)
355{
357
358 // adaptor functor to utilize the Eigen non-linear solver
359 auto functor = make_realvector_adaptor<false>(computeResidual, computeJacobian);
360 Eigen::HybridNonLinearSolver<decltype(functor), NSReal> solver(functor);
361 V guess_eigen(3);
362 guess_eigen << guess(0), guess(1), guess(2);
363 auto status = solver.solve(guess_eigen);
364 guess(0) = guess_eigen(0);
365 guess(1) = guess_eigen(1);
366 guess(2) = guess_eigen(2);
367
368 if (status == Eigen::HybridNonLinearSolverSpace::RelativeErrorTooSmall)
369 _state = State::CONVERGED_REL;
370 else
371 _state = State::NOT_CONVERGED;
372}
373
374template <bool is_ad>
375template <typename R, typename J, typename B>
376void
378 R & computeResidual,
379 J & computeJacobian,
380 B & computeBounds)
381{
382 auto functor = make_real_adaptor<false>(computeResidual, computeJacobian);
383 Eigen::HybridNonLinearSolver<decltype(functor), NSReal> solver(functor);
384
386 guess_eigen << guess;
387
388 auto status = solver.solveInit(guess_eigen);
389 if (status == Eigen::HybridNonLinearSolverSpace::ImproperInputParameters)
390 return;
391
392 bool bounds_hit = false;
393 while (status == Eigen::HybridNonLinearSolverSpace::Running)
394 {
395 status = solver.solveOneStep(guess_eigen);
396 const std::pair<Real, Real> & bounds = computeBounds();
397
398 // Snap to bounds. Terminate solve if we snap twice consecutively.
399 if (guess_eigen(0) < bounds.first || guess_eigen(0) > bounds.second)
400 {
401 if (guess_eigen(0) < bounds.first)
402 guess_eigen(0) = bounds.first;
403 else
404 guess_eigen(0) = bounds.second;
405
406 if (bounds_hit)
407 {
408 _state = State::CONVERGED_BOUNDS;
409 return;
410 }
411
412 bounds_hit = true;
413 }
414 }
415
416 if (status == Eigen::HybridNonLinearSolverSpace::RelativeErrorTooSmall)
417 _state = State::CONVERGED_REL;
418 else
419 _state = State::NOT_CONVERGED;
420
421 guess = guess_eigen(0);
422}
423
424template <bool is_ad>
425template <typename V, typename T>
426void
428{
429 V delta;
430 V residual;
432 sizeItems(guess, residual, jacobian);
433
434 _n_iterations = 0;
435 compute(guess, residual, jacobian);
436
437 // compute first residual norm for relative convergence checks
438 auto r0_square = normSquare(residual);
439 if (r0_square == 0)
440 {
441 _state = State::EXACT_GUESS;
442 return;
443 }
444 auto r_square = r0_square;
445
446 // perform non-linear iterations
447 while (_n_iterations < _max_iterations)
448 {
449 // check convergence
450 if (_n_iterations >= _min_iterations && isConverged(r0_square, r_square, /*acceptable=*/false))
451 return;
452
453 // solve and apply next increment
454 linear(jacobian, delta, residual);
455
456 // Check if step size is smaller than the floating point tolerance
457 if (isRelSmall(delta, guess, _delta_thresh))
458 {
459 _state = State::CONVERGED_XTOL;
460 return;
461 }
462
463 guess -= delta;
464 _n_iterations++;
465
466 // compute residual and jacobian for the next iteration
467 compute(guess, residual, jacobian);
468
469 r_square = normSquare(residual);
470 }
471
475 if (!isConverged(r0_square, r_square, /*acceptable=*/true))
476 _state = State::NOT_CONVERGED;
477}
478
479template <bool is_ad>
480template <typename V, typename T, typename C>
481void
482NestedSolveTempl<is_ad>::nonlinearDamped(V & guess, T && compute, C && computeCondition)
483{
484 V delta;
485 V residual;
487 sizeItems(guess, residual, jacobian);
488
489 _n_iterations = 0;
490 compute(guess, residual, jacobian);
491
492 // compute first residual norm for relative convergence checks
493 auto r0_square = normSquare(residual);
494 if (r0_square == 0)
495 {
496 _state = State::EXACT_GUESS;
497 return;
498 }
499 auto r_square = r0_square;
500
501 // perform non-linear iterations
502 while (_n_iterations < _max_iterations)
503 {
504 // check convergence
505 if (_n_iterations >= _min_iterations && isConverged(r0_square, r_square, /*acceptable=*/false))
506 return;
507
508 // solve and apply next increment
509 linear(jacobian, delta, residual);
510
511 // Check if step size is smaller than the floating point tolerance
512 if (isRelSmall(delta, guess, _delta_thresh))
513 {
514 _state = State::CONVERGED_XTOL;
515 return;
516 }
517
518 Real alpha = 1;
519 unsigned int damping_iterations = 0;
520 auto prev_guess = guess;
521 guess -= delta;
522
523 while (!computeCondition(guess) && (damping_iterations < _max_damping_iterations))
524 {
525 alpha *= _damping_factor;
526 guess = prev_guess - alpha * delta;
527 damping_iterations += 1;
528 }
529 _n_iterations++;
530
531 // compute residual and jacobian for the next iteration
532 compute(guess, residual, jacobian);
533
534 r_square = normSquare(residual);
535 }
536
537 // if we exceed the max iterations, we could still be converged (considering the acceptable
538 // multiplier)
539 if (!isConverged(r0_square, r_square, /*acceptable=*/true))
540 _state = State::NOT_CONVERGED;
541}
542
543template <bool is_ad>
544template <typename J, typename V>
545void
546NestedSolveTempl<is_ad>::linear(const J & A, V & x, const V & b) const
547{
548 // we could make the linear solve method configurable here
549 x = A.partialPivLu().solve(b);
550}
551
552template <bool is_ad>
553template <typename V>
554Real
556{
557 // we currently cannot get the raw_value of an AD Eigen Matrix, so we loop over components
558 Real norm_square = 0.0;
559 for (const auto i : index_range(v))
560 norm_square += Utility::pow<2>(MetaPhysicL::raw_value(v.data()[i]));
561 return norm_square;
562}
563
568namespace NestedSolveInternal
569{
570
571template <>
573{
574 using type = Real;
575};
576
577template <>
582
583template <>
584struct CorrespondingJacobianTempl<RealVectorValue>
585{
587};
588
589template <>
594
595template <>
596struct CorrespondingJacobianTempl<typename NestedSolveTempl<false>::DynamicVector>
597{
599};
600
601template <>
602struct CorrespondingJacobianTempl<typename NestedSolveTempl<true>::DynamicVector>
603{
605};
606
607template <int N>
608struct CorrespondingJacobianTempl<typename Eigen::Matrix<Real, N, 1>>
609{
610 using type = Eigen::Matrix<Real, N, N>;
611};
612
613template <int N>
614struct CorrespondingJacobianTempl<typename Eigen::Matrix<ADReal, N, 1>>
615{
616 using type = Eigen::Matrix<ADReal, N, N>;
617};
618
623template <bool is_ad, typename R, typename J, bool store_residual_norm>
625{
627
628public:
629 DynamicMatrixEigenAdaptorFunctor(R & residual_lambda, J & jacobian_lambda)
630 : _residual_lambda(residual_lambda), _jacobian_lambda(jacobian_lambda)
631 {
632 }
633 int operator()(V & guess, V & residual)
634 {
635 _residual_lambda(guess, residual);
636 if constexpr (store_residual_norm)
638 return 0;
639 }
640 int df(V & guess, typename NestedSolveTempl<is_ad>::template CorrespondingJacobian<V> & jacobian)
641 {
642 _jacobian_lambda(guess, jacobian);
643 return 0;
644 }
645
646 const Real & getResidualNorm()
647 {
648 if constexpr (store_residual_norm)
649 return _residual_norm;
650 }
651
652private:
655
657};
658
663template <bool is_ad, typename R, typename J, bool store_residual_norm>
665{
667
668public:
669 RealEigenAdaptorFunctor(R & residual_lambda, J & jacobian_lambda)
670 : _residual_lambda(residual_lambda), _jacobian_lambda(jacobian_lambda)
671 {
672 }
673 int operator()(V & guess, V & residual)
674 {
675 _residual_lambda(guess(0), residual(0));
676 if constexpr (store_residual_norm)
678 return 0;
679 }
680 int df(V & guess, typename NestedSolveTempl<is_ad>::template CorrespondingJacobian<V> & jacobian)
681 {
682 _jacobian_lambda(guess(0), jacobian(0, 0));
683 return 0;
684 }
685
686 const Real & getResidualNorm()
687 {
688 if constexpr (store_residual_norm)
689 return _residual_norm;
690 }
691
692private:
695
697};
698
703template <bool is_ad, typename R, typename J, bool store_residual_norm>
705{
707
708public:
709 RealVectorEigenAdaptorFunctor(R & residual_lambda, J & jacobian_lambda)
710 : _residual_lambda(residual_lambda), _jacobian_lambda(jacobian_lambda)
711 {
712 }
713 int operator()(V & guess, V & residual)
714 {
715 typename NestedSolveTempl<is_ad>::NSRealVectorValue guess_moose(guess(0), guess(1), guess(2));
716 typename NestedSolveTempl<is_ad>::NSRealVectorValue residual_moose;
717 _residual_lambda(guess_moose, residual_moose);
718 residual(0) = residual_moose(0);
719 residual(1) = residual_moose(1);
720 residual(2) = residual_moose(2);
721 if constexpr (store_residual_norm)
723 return 0;
724 }
725 int df(V & guess, typename NestedSolveTempl<is_ad>::template CorrespondingJacobian<V> & jacobian)
726 {
727 typename NestedSolveTempl<is_ad>::NSRealVectorValue guess_moose(guess(0), guess(1), guess(2));
728 typename NestedSolveTempl<is_ad>::NSRankTwoTensor jacobian_moose;
729 _jacobian_lambda(guess_moose, jacobian_moose);
730 jacobian =
731 Eigen::Map<typename NestedSolveTempl<is_ad>::DynamicMatrix>(&jacobian_moose(0, 0), 3, 3);
732 return 0;
733 }
734
735 const Real & getResidualNorm()
736 {
737 if constexpr (store_residual_norm)
738 return _residual_norm;
739 }
740
741private:
744
746};
747
748} // namespace NestedSolveInternal
749
750template <bool is_ad>
751template <bool store_residual_norm, typename R, typename J>
752auto
753NestedSolveTempl<is_ad>::make_adaptor(R & residual_lambda, J & jacobian_lambda)
754{
756 residual_lambda, jacobian_lambda);
757}
758template <bool is_ad>
759template <bool store_residual_norm, typename R, typename J>
760auto
761NestedSolveTempl<is_ad>::make_real_adaptor(R & residual_lambda, J & jacobian_lambda)
762{
764 residual_lambda, jacobian_lambda);
765}
766
767template <bool is_ad>
768template <bool store_residual_norm, typename R, typename J>
769auto
770NestedSolveTempl<is_ad>::make_realvector_adaptor(R & residual_lambda, J & jacobian_lambda)
771{
773 residual_lambda, jacobian_lambda);
774}
775
776// lambda to check for convergence and set the state accordingly
777template <bool is_ad>
778bool
779NestedSolveTempl<is_ad>::isConverged(const Real r0_square, Real r_square, bool acceptable)
780{
781 if (acceptable)
782 r_square /= _acceptable_multiplier * _acceptable_multiplier;
783 if (r_square < _absolute_tolerance_square)
784 {
785 _state = acceptable ? State::CONVERGED_ACCEPTABLE_ABS : State::CONVERGED_ABS;
786 return true;
787 }
788 if (r_square / r0_square < _relative_tolerance_square)
789 {
790 _state = acceptable ? State::CONVERGED_ACCEPTABLE_REL : State::CONVERGED_REL;
791 return true;
792 }
793 return false;
794}
795
RankTwoTensorTempl< ADReal > ADRankTwoTensor
DualNumber< Real, DNDerivativeType, true > ADReal
NestedSolveTempl< false > NestedSolve
NestedSolveTempl< true > ADNestedSolve
RankTwoTensorTempl< Real > RankTwoTensor
The main MOOSE class responsible for handling user-defined parameters in almost every MOOSE system.
Adaptor functor for Eigen::Matrix based residual and Jacobian types.
typename NestedSolveTempl< is_ad >::DynamicVector V
DynamicMatrixEigenAdaptorFunctor(R &residual_lambda, J &jacobian_lambda)
int df(V &guess, typename NestedSolveTempl< is_ad >::template CorrespondingJacobian< V > &jacobian)
Adaptor functor for scalar Real valued residual and Jacobian types.
RealEigenAdaptorFunctor(R &residual_lambda, J &jacobian_lambda)
typename NestedSolveTempl< is_ad >::DynamicVector V
int df(V &guess, typename NestedSolveTempl< is_ad >::template CorrespondingJacobian< V > &jacobian)
Adaptor functor for MOOSE RealVectorValue/RankTwoTensor residual and Jacobian types.
RealVectorEigenAdaptorFunctor(R &residual_lambda, J &jacobian_lambda)
typename NestedSolveTempl< is_ad >::DynamicVector V
int df(V &guess, typename NestedSolveTempl< is_ad >::template CorrespondingJacobian< V > &jacobian)
NestedSolveTempl<is_ad> and its instantiations NestedSolve and ADNestedSolve are utility classes that...
Definition NestedSolve.h:43
auto make_realvector_adaptor(R &residual, J &jacobian)
void nonlinearDamped(V &guess, T &&compute, C &&computeCondition)
Solve the N*N nonlinear equation system using the damped Netwon-Raphson loop.
static Real acceptableMultiplierDefault()
auto make_adaptor(R &residual, J &jacobian)
Build a suitable Eigen adaptor functors to interface between moose and Eigen types.
typename std::conditional< N==1, NSReal, typename std::conditional< N==0, NestedSolveTempl< is_ad >::DynamicVector, Eigen::Matrix< NSReal, N, 1 > >::type >::type Value
Residual and solution type.
Definition NestedSolve.h:75
unsigned int _max_iterations
const State & getState() const
Get the solver state.
void linear(const NSReal &A, NSReal &x, const NSReal &b) const
void sizeItems(const V &, V &, T &) const
Sizing is a no-op for compile time sized types (and scalars)
static Real absoluteToleranceDefault()
State _state
current solver state
typename NestedSolveInternal::CorrespondingJacobianTempl< T >::type CorrespondingJacobian
Definition NestedSolve.h:65
static unsigned int maxIterationsDefault()
Moose::GenericType< RankTwoTensor, is_ad > NSRankTwoTensor
Definition NestedSolve.h:53
Real _damping_factor
Damping factor.
Real _absolute_tolerance_square
bool isConverged(Real r0_square, Real r_square, bool acceptable)
Convergence check (updates _status)
void nonlinear(V &guess, T &&compute)
Solve the N*N nonlinear equation system using a built-in Netwon-Raphson loop.
static bool isRelSmall(const V &a, const V &b, const V &c)
Check if |a| < |b * c| for all elements in a and b. This checks if 'a' is small relative to.
void sizeItems(const NestedSolveTempl< is_ad >::DynamicVector &guess, NestedSolveTempl< is_ad >::DynamicVector &residual, NestedSolveTempl< is_ad >::DynamicMatrix &jacobian) const
Size a dynamic Jacobian matrix correctly.
Definition NestedSolve.C:83
static Real relativeToleranceDefault()
default values
auto make_real_adaptor(R &residual, J &jacobian)
typename std::conditional< N==1, NSReal, typename std::conditional< N==0, NestedSolveTempl< is_ad >::DynamicMatrix, Eigen::Matrix< NSReal, N, N > >::type >::type Jacobian
Jacobian matrix type.
Definition NestedSolve.h:84
State
possible solver states
Moose::GenericType< Real, is_ad > NSReal
AD/non-AD switched type shortcuts.
Definition NestedSolve.h:51
Eigen::Matrix< NSReal, Eigen::Dynamic, 1 > DynamicVector
Eigen type shortcuts.
Definition NestedSolve.h:57
Moose::GenericType< RealVectorValue, is_ad > NSRealVectorValue
Definition NestedSolve.h:52
unsigned int _max_damping_iterations
static InputParameters validParams()
Definition NestedSolve.C:16
static unsigned int minIterationsDefault()
static Real xToleranceDefault()
void setRelativeTolerance(Real rel)
void setAbsoluteTolerance(Real abs)
Real _relative_tolerance_square
Real _acceptable_multiplier
void nonlinearBounded(NSReal &guess, R &computeResidual, J &computeJacobian, B &computeBounds)
Perform a bounded solve use Eigen::HybridNonLinearSolver.
Real _delta_thresh
Threshold for minimum step size of linear iterations.
static unsigned int maxDampingIterationsDefault()
void nonlinear(DynamicVector &guess, R &computeResidual, J &computeJacobian)
unsigned int _min_iterations
void linear(const J &A, V &x, const V &b) const
Solve A*x=b for x.
void setAcceptableMultiplier(Real am)
static Real normSquare(const V &v)
Compute squared norm of v (dropping derivatives as this is only for convergence checking)
Eigen::Matrix< NSReal, Eigen::Dynamic, Eigen::Dynamic > DynamicMatrix
Definition NestedSolve.h:58
void nonlinearTight(DynamicVector &guess, R &computeResidual, J &computeJacobian)
std::size_t _n_iterations
number of nested iterations
const std::size_t & getIterations()
Get the number of iterations from the last solve.
static Real dampingFactorDefault()
Definition JsonIO.h:69
auto raw_value(const Eigen::Map< T > &in)
typename std::conditional< is_ad, typename ADType< T >::type, T >::type GenericType
Definition MooseTypes.h:694
Internal use namespace that contains template helpers to map each residual type to its corresponding ...
Definition NestedSolve.h:31
Deduce the Jacobian type from the solution type.
Definition NestedSolve.h:63