Line data Source code
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 "SolveObject.h"
13 :
14 : #include "SolverParams.h"
15 : #include "PetscSupport.h"
16 :
17 : #include "ExecFlagEnum.h"
18 : #include <petsctao.h>
19 :
20 : #include "libmesh/petsc_vector.h"
21 : #include "libmesh/petsc_matrix.h"
22 :
23 : class OptimizationReporterBase;
24 :
25 : /**
26 : * solveObject to interface with Petsc Tao
27 : */
28 : class OptimizeSolve : public SolveObject
29 : {
30 : public:
31 : static InputParameters validParams();
32 : OptimizeSolve(Executioner & ex);
33 :
34 : virtual bool solve() override;
35 :
36 : const OptimizationReporterBase & getOptimizationReporter() const { return *_obj_function; }
37 :
38 : /**
39 : * Record tao TaoGetSolutionStatus data for output by a reporter
40 : * @param tot_iters total solves per iteration
41 : * @param gnorm gradient norm per iteration
42 : * @param obj_iters number of objective solves per iteration
43 : * @param cnorm infeasibility norm per iteration
44 : * @param grad_iters gradient solves per iteration
45 : * @param xdiff step length per iteration
46 : * @param hess_iters Hessian solves per iteration
47 : * @param f objective value per iteration
48 : * @param tot_solves total solves per iteration
49 : */
50 : void getTaoSolutionStatus(std::vector<int> & tot_iters,
51 : std::vector<double> & gnorm,
52 : std::vector<int> & obj_iters,
53 : std::vector<double> & cnorm,
54 : std::vector<int> & grad_iters,
55 : std::vector<double> & xdiff,
56 : std::vector<int> & hess_iters,
57 : std::vector<double> & f,
58 : std::vector<int> & tot_solves) const;
59 :
60 : protected:
61 : /// Bounds routine
62 : virtual PetscErrorCode variableBounds(Tao tao);
63 :
64 : /// Objective routine
65 : virtual Real objectiveFunction();
66 :
67 : /// Gradient routine
68 : virtual void gradientFunction(libMesh::PetscVector<Number> & gradient);
69 :
70 : /// Hessian application routine
71 : virtual PetscErrorCode applyHessian(libMesh::PetscVector<Number> & s,
72 : libMesh::PetscVector<Number> & Hs);
73 :
74 : /// Communicator used for operations
75 : const libMesh::Parallel::Communicator _my_comm;
76 :
77 : /// List of execute flags for when to solve the system
78 : const ExecFlagEnum & _solve_on;
79 :
80 : /// objective function defining objective, gradient, and hessian
81 : OptimizationReporterBase * _obj_function = nullptr;
82 :
83 : ///function to get the objective reporter
84 2262 : OptimizationReporterBase * getObjFunction() { return _obj_function; }
85 :
86 : /// Tao optimization object
87 : Tao _tao;
88 :
89 : private:
90 : /// control optimization executioner output
91 : bool _verbose;
92 :
93 : /// Use time step as the iteration counter for purposes of outputting
94 : bool _output_opt_iters;
95 :
96 : ///@{
97 : /// count individual solves for output
98 : int _obj_iterate = 0;
99 : int _grad_iterate = 0;
100 : int _hess_iterate = 0;
101 : ///@}
102 : /// total solves per iteration
103 : std::vector<int> _total_iterate_vec;
104 : /// number of objective solves per iteration
105 : std::vector<int> _obj_iterate_vec;
106 : /// gradient solves per iteration
107 : std::vector<int> _grad_iterate_vec;
108 : /// Hessian solves per iteration
109 : std::vector<int> _hess_iterate_vec;
110 : /// total solves per iteration
111 : std::vector<int> _function_solve_vec;
112 : /// objective value per iteration
113 : std::vector<double> _f_vec;
114 : /// gradient norm per iteration
115 : std::vector<double> _gnorm_vec;
116 : /// infeasibility norm per iteration
117 : std::vector<double> _cnorm_vec;
118 : /// step length per iteration
119 : std::vector<double> _xdiff_vec;
120 :
121 : ///@{
122 : /// These are needed to reset the petsc options for the optimization solve
123 : /// using Moose::PetscSupport::petscSetOptions
124 : /// This only sets the finite difference options, the other optimizeSolve
125 : /// options are set-up in TAO using TaoSetFromOptions()
126 : Moose::PetscSupport::PetscOptions _petsc_options;
127 : SolverParams _solver_params;
128 : ///@}
129 :
130 : /// Here is where we call tao and solve
131 : PetscErrorCode taoSolve();
132 :
133 : /// output optimization iteration solve data
134 : void setTaoSolutionStatus(double f, int its, double gnorm, double cnorm, double xdiff);
135 :
136 : ///@{
137 : /// Function wrappers for tao
138 : static PetscErrorCode objectiveFunctionWrapper(Tao tao, Vec x, Real * objective, void * ctx);
139 : static PetscErrorCode hessianFunctionWrapper(Tao tao, Vec x, Mat hessian, Mat pc, void * ctx);
140 : static PetscErrorCode applyHessianWrapper(Mat H, Vec s, Vec Hs);
141 : static PetscErrorCode
142 : objectiveAndGradientFunctionWrapper(Tao tao, Vec x, Real * objective, Vec gradient, void * ctx);
143 : static PetscErrorCode variableBoundsWrapper(Tao /*tao*/, Vec xl, Vec xu, void * ctx);
144 : static PetscErrorCode monitor(Tao tao, void * ctx);
145 : static PetscErrorCode equalityFunctionWrapper(Tao tao, Vec x, Vec ce, void * ctx);
146 : static PetscErrorCode
147 : equalityGradientFunctionWrapper(Tao tao, Vec x, Mat gradient_e, Mat gradient_epre, void * ctx);
148 : static PetscErrorCode inequalityFunctionWrapper(Tao tao, Vec x, Vec ci, void * ctx);
149 : static PetscErrorCode
150 : inequalityGradientFunctionWrapper(Tao tao, Vec x, Mat gradient_i, Mat gradient_ipre, void * ctx);
151 : ///@}
152 :
153 : /// Enum of tao solver types
154 : const enum class TaoSolverEnum {
155 : NEWTON_TRUST_REGION,
156 : BOUNDED_NEWTON_TRUST_REGION,
157 : BOUNDED_CONJUGATE_GRADIENT,
158 : NEWTON_LINE_SEARCH,
159 : BOUNDED_NEWTON_LINE_SEARCH,
160 : BOUNDED_QUASI_NEWTON_TRUST_REGION,
161 : NEWTON_TRUST_LINE,
162 : BOUNDED_NEWTON_TRUST_LINE,
163 : QUASI_NEWTON,
164 : BOUNDED_QUASI_NEWTON,
165 : NELDER_MEAD,
166 : BOUNDED_QUASI_NEWTON_LINE_SEARCH,
167 : ORTHANT_QUASI_NEWTON,
168 : GRADIENT_PROJECTION_CONJUGATE_GRADIENT,
169 : BUNDLE_RISK_MIN,
170 : AUGMENTED_LAGRANGIAN_MULTIPLIER_METHOD
171 : } _tao_solver_enum;
172 :
173 : /// Number of parameters being optimized
174 : dof_id_type _ndof;
175 :
176 : /// Parameters (solution) given to TAO
177 : std::unique_ptr<libMesh::PetscVector<Number>> _parameters;
178 :
179 : /// Hessian (matrix) - usually a matrix-free representation
180 : Mat _hessian;
181 :
182 : /// Equality constraint vector
183 : Vec _ce;
184 :
185 : /// Inequality constraint vector
186 : Vec _ci;
187 :
188 : /// Equality constraint gradient
189 : Mat _gradient_e;
190 :
191 : /// Inequality constraint gradient
192 : Mat _gradient_i;
193 :
194 : /// Used for creating petsc structures when using the ALMM algorithm
195 : PetscErrorCode taoALCreate();
196 : /// Used for destroying petsc structures when using the ALMM algorithm
197 : PetscErrorCode taoALDestroy();
198 : };
|