MMA.H
Go to the documentation of this file.
1 /*---------------------------------------------------------------------------*\
2  ========= |
3  \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
4  \\ / O peration |
5  \\ / A nd | www.openfoam.com
6  \\/ M anipulation |
7 -------------------------------------------------------------------------------
8  Copyright (C) 2020-2023 PCOpt/NTUA
9  Copyright (C) 2020-2023 FOSS GP
10 -------------------------------------------------------------------------------
11 License
12  This file is part of OpenFOAM.
13 
14  OpenFOAM is free software: you can redistribute it and/or modify it
15  under the terms of the GNU General Public License as published by
16  the Free Software Foundation, either version 3 of the License, or
17  (at your option) any later version.
18 
19  OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
20  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
21  FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
22  for more details.
23 
24  You should have received a copy of the GNU General Public License
25  along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
26 
27 
28 Class
29  Foam::MMA
30 
31 Description
32  Update design variables using the Method of Moving Assymptotes.
33  Can handle inequality constraints.
34 
35  Reference:
36  \verbatim
37  Svanberg, K. (1987)
38  The method of moving asymptotes—a new method for structural
39  optimization
40  International Journal for Numerical Methods in Engineering, 24(2),
41  359-373.
42  https://doi.org/10.1002/nme.1620240207
43  \endverbatim
44 
45 SourceFiles
46  MMA.C
47 
48 \*---------------------------------------------------------------------------*/
49 
50 #ifndef MMA_H
51 #define MMA_H
52 
54 #include "updateMethod.H"
55 #include "PtrList.H"
56 
57 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
58 
59 namespace Foam
60 {
61 
62 /*---------------------------------------------------------------------------*\
63  Class MMA Declaration
64 \*---------------------------------------------------------------------------*/
65 
66 class MMA
67 :
69  public updateMethod
70 {
71 protected:
72 
73  // Protected data
74 
75  //- The previous design variables. Used to compute new bounds
77 
78  //- The twice previous design variables. Used to compute new bounds
80 
81  //- The set of design variables being updated during the subproblem.
82  // Correction will end up being the difference of this and the
83  // old values of the design variables
85 
86  //- Old objective value
87  // Needed by GCMMA
88  scalar oldObjectiveValue_;
89 
90  //- Old constraint values
91  // Needed by GCMMA
93 
94  //- Objective/Constraint values and approximations in the new point
95  // Needed by GCMMA
97 
98  //- Second term in the approximation function
99  scalar z_;
101  //- Term multiplying z in the objective function
102  scalar alpha0_;
103 
104  //- Terms multyplying z in the constraint functions
106 
107  //- y in the constraints functions
108  scalarField y_;
109 
110  //- y multipliers in the objective function
111  scalarField c_;
113  //- y^2 multipliers in the objective function
114  scalarField d_;
115 
116  //- Lower design variables asymptotes
118 
119  //- Upper design variables asymptotes
121 
122  //- Lower design variables constraints
123  scalarField a_;
124 
125  //- Upper design variables constraints
126  scalarField b_;
128  //- Constants in the (p,q) functions.
129  // Size is cValues_.size() + 1 (the objective)
131 
132  //- Bound the rho value with an upper value?
133  bool boundRho_;
134 
135  //- Correct the design variables
136  bool correctDVs_;
138  // Dual variables
139 
140  //- Constraint Lagrange multipliers
143  //- Lagrange multipliers for the lower limits constraints
145 
146  //- Lagrange multipliers for the upper limits constraints
148 
149  //- Lagrange multipliers for the y constraints
151 
152  //- Lagrange multiplier for the z constraint
153  scalar zeta_;
154 
155  //- Slack variables for the inequality constraints
156  scalarField s_;
158 
159  // Fields holding updates of the design, Lagrange and slack variables
160 
162  scalar deltaZ_;
166  scalar deltaZeta_;
170 
171 
172  //- Infinitesimal quantity
173  // Updated during the inner iterations of the subproblem
174  scalar eps_;
175 
176  //- Maxmimum number of Newton iterations for the subproblem
177  label maxNewtonIters_;
178 
179  //- Maxmimum number of line search iterations for each iteration of the
180  //- subproblem
182 
183  //- Initialize every subproblem with x = 0.5*(a + b)
184  //- and reset Lagrange multipliers
185  // The solution of the subproblem can become relatively expensive
186  // in some cases, hence the GCMMA subproblems are usually
187  // initialized with the solution of the previous inner iteration,
188  // to save up some time. Occassionally, this can cause the solution
189  // of the subproblem to be trapped in a non-feasible point.
190  // In such cases, the solution of each subproblem could be
191  // initialized from scratch
193 
194 
195  // Constant parameters
197  //- Lower assymprote reduction rate
198  scalar asymDecr_;
199 
200  //- Upper assymprote increase rate
201  scalar asymIncr_;
202 
203  //- Used to update the assymptotes in the first optimisation cycle
204  scalar sInit_;
205 
206  //- Movement of the unatainable upper and lower bounds
207  scalar move_;
208 
209  //- Constant in p, q functions
210  scalar raa0_;
213  // Parameters related to the update of rho in GCMMA
215  //- Multiplier of the mean derivative used for the initialisation
216  //- of rho
219  //- Multiplier for the max. rho value during its update
220  scalar maxRhoMult_;
221 
222  //- Change rho constants in each iteration?
223  bool variableRho_;
224 
225  //- Change rho constants in each iteration?
228  //- The rho values obtained by the dynamic rho initialisation
229  //- might be too conservative. Multiply with this number to relax
230  //- them
231  scalar dynamicRhoMult_;
233 
234  // Normalisation based on the gradient
235 
236  //- Perform the normalisation
237  bool normalise_;
239  //- Perform the normalisation in each optimisation cycle
241 
242  //- Normalisation factor for the objective
244 
245  //- Normalisation factors for the constraints
247 
248  //- Constaint weight after the normalisation
249  scalar cw_;
250 
251  //- Constaint weight after the normalisation
253 
254 
255  // Protected Member Functions
256 
257  //- Update sizes of fields related to the active design variables
258  void updateSizes();
259 
260  //- Initialize rho constants in the (p, q) functions
261  // These control how aggressive or conservative the method will be
262  void initializeRho();
263 
264  //- Update the bounds associated with the design variables
265  void updateBounds();
266 
267  //- Allocate fields related to constraints
268  void initialize();
269 
270  //- Store old objcective and constraint values
271  // Needed by GCMMA
272  void storeOldValues();
273 
274  //- p and q functions, used to approximate the objective and contraints
275  // Computed based on the current set of design variables, not updated
276  // during the iterations of the subproblem
278  (
279  const scalarField& derivs,
280  const scalar r,
281  const scalarField& x
282  );
283  tmp<scalarField> p(const scalarField& derivs, const scalar r);
285  (
286  const scalarField& derivs,
287  const scalar r,
288  const scalarField& x
289  );
290  tmp<scalarField> q(const scalarField& derivs, const scalar r);
291 
292  //- g of all constraint functions
293  // Computed using the current set of design variables, updated during
294  // the solution of the subproblem
295  tmp<scalarField> gConstr(const scalarField& vars);
296 
297  //- The rhs of the contraint approximations.
298  // Always computed using the current (frozen) set of design variables
300 
301  //- p and q functions, using the dual lamda
305  //- Zero the updates computed in the previous optimisation cycle
306  void zeroUpdates();
307 
308  //- Computation of the approximate function
309  scalar fTilda
310  (
311  const scalarField& xInit,
312  const scalarField& x,
313  const scalar f,
314  const scalarField& dfdx,
315  const scalar rho
316  );
317 
318  //- Read in scalarField from self (potentially in binary), or allocate
319  //- field with the size of the active design variables and given value
321  (
322  const word& name,
323  const label size,
324  const scalar value = Zero
325  );
326 
327  //- Read in scalarField from self (potentially in binary), or allocate
328  //- field with the size of the active design variables and given value
330  (
332  const word& name,
333  const label size,
334  const scalarField& defaultField
335  );
336 
337 
338  // Functions related to the solution of the primal-dual subproblem
340  //- Compute direction for the Newton problem
341  void computeNewtonDirection();
342 
343  //- Perform line search and return max residual corresponding to
344  //- the updated solution
345  scalar lineSearch();
346 
347  //- Update the current solution using the known direction and the
348  //- given step length
349  void updateSolution(const scalar step);
350 
351  //- Adjust step to satisfy cireteria
352  void adjustStep
353  (
354  scalar& step,
355  const scalar value,
356  const scalar update
357  );
358 
359  //- Compute and return residuals based on the current solution
361 
362 
363  //- Normalise the objective and constraints if necessary
364  void normalise();
365 
366 
367 private:
368 
369  // Private Member Functions
370 
371  //- No copy construct
372  MMA(const MMA&);
373 
374  //- No copy assignment
375  void operator=(const MMA&);
376 
377 
378 public:
379 
380  //- Runtime type information
381  TypeName("MMA");
382 
383 
384  // Constructors
385 
386  //- Construct from components
387  MMA
388  (
389  const fvMesh& mesh,
390  const dictionary& dict,
391  autoPtr<designVariables>& designVars,
392  const label nConstraints,
393  const word& type
394  );
395 
396 
397  //- Destructor
398  virtual ~MMA() = default;
399 
400 
401  // Member Functions
402 
403  //- Compute design variables correction
404  void computeCorrection();
405 
406  //- Solve subproblem using a Newton optimiser
407  void solveSubproblem();
408 
409  // Functions needed by GCMMA
410 
411  //- Compute objective/constraint values and their approximations
412  // Needed to check convergence and update rho, if necessary
414 
415  //- Get objective/constraint values and their approximations
417 
418  //- Update rho value if needed
419  void updateRho();
420 
421  //- Get rho value if needed
422  const scalarField& getRho() const;
423 
424  //- Set variable rho
425  void setVariableRho(bool varRho = true);
426 
427  //- Checks convergence of GCMMA
428  bool converged();
429 
430 
431  //- Write useful quantities to files
432  virtual bool writeData(Ostream& os) const;
433 };
434 
435 
436 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
437 
438 } // End namespace Foam
439 
440 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
441 
442 #endif
443 
444 // ************************************************************************* //
tmp< scalarField > pLamda()
p and q functions, using the dual lamda
Definition: MMA.C:371
scalarField ksi_
Lagrange multipliers for the lower limits constraints.
Definition: MMA.H:186
scalar deltaZeta_
Definition: MMA.H:216
dictionary dict
void setVariableRho(bool varRho=true)
Set variable rho.
Definition: MMA.C:1118
void solveSubproblem()
Solve subproblem using a Newton optimiser.
Definition: MMA.C:999
rDeltaTY field()
bool correctDVs_
Correct the design variables.
Definition: MMA.H:174
Abstract base class for optimisation methods supporting constraints. Does not add functionality to up...
scalarField alpha_
Terms multyplying z in the constraint functions.
Definition: MMA.H:122
void computeCorrection()
Compute design variables correction.
Definition: MMA.C:967
void setOrDefaultScalarField(scalarField &field, const word &name, const label size, const scalarField &defaultField)
Read in scalarField from self (potentially in binary), or allocate field with the size of the active ...
Definition: MMA.C:460
label nConstraints() const
Get the number of constraints.
Definition: updateMethod.C:393
tmp< scalarField > b()
The rhs of the contraint approximations.
Definition: MMA.C:362
A list of keyword definitions, which are a keyword followed by a number of values (eg...
Definition: dictionary.H:129
scalarField deltaY_
Definition: MMA.H:214
scalarField lamda_
Constraint Lagrange multipliers.
Definition: MMA.H:181
tmp< scalarField > qLamda()
Definition: MMA.C:389
scalarField deltaKsi_
Definition: MMA.H:219
scalarField s_
Slack variables for the inequality constraints.
Definition: MMA.H:206
void computeNewtonDirection()
Compute direction for the Newton problem.
Definition: MMA.C:478
Abstract base class for optimisation methods.
Definition: updateMethod.H:50
label maxNewtonIters_
Maxmimum number of Newton iterations for the subproblem.
Definition: MMA.H:232
void updateValuesAndApproximations()
Compute objective/constraint values and their approximations.
Definition: MMA.C:1047
void updateSolution(const scalar step)
Update the current solution using the known direction and the given step length.
Definition: MMA.C:743
scalarField deltaX_
Definition: MMA.H:213
virtual bool writeData(Ostream &os) const
Write useful quantities to files.
Definition: MMA.C:1144
tmp< scalarField > p(const scalarField &derivs, const scalar r, const scalarField &x)
p and q functions, used to approximate the objective and contraints
Definition: MMA.C:261
bool converged()
Checks convergence of GCMMA.
Definition: MMA.C:1124
autoPtr< scalar > Jnorm_
Normalisation factor for the objective.
Definition: MMA.H:329
virtual ~MMA()=default
Destructor.
scalar asymIncr_
Upper assymprote increase rate.
Definition: MMA.H:265
PtrList< scalarField > valsAndApproxs_
Objective/Constraint values and approximations in the new point.
Definition: MMA.H:107
scalar asymDecr_
Lower assymprote reduction rate.
Definition: MMA.H:260
scalarField rho_
Constants in the (p,q) functions.
Definition: MMA.H:164
scalarField b_
Upper design variables constraints.
Definition: MMA.H:157
scalar sInit_
Used to update the assymptotes in the first optimisation cycle.
Definition: MMA.H:270
scalarField d_
y^2 multipliers in the objective function
Definition: MMA.H:137
scalarField lower_
Lower design variables asymptotes.
Definition: MMA.H:142
fileName::Type type(const fileName &name, const bool followLink=true)
Return the file type: DIRECTORY or FILE, normally following symbolic links.
Definition: POSIX.C:799
tmp< scalarField > q(const scalarField &derivs, const scalar r, const scalarField &x)
Definition: MMA.C:301
void normalise()
Normalise the objective and constraints if necessary.
Definition: MMA.C:821
dynamicFvMesh & mesh
scalarField mu_
Lagrange multipliers for the y constraints.
Definition: MMA.H:196
tmp< scalarField > Cnorm_
Normalisation factors for the constraints.
Definition: MMA.H:334
tmp< scalarField > getOrDefaultScalarField(const word &name, const label size, const scalar value=Zero)
Read in scalarField from self (potentially in binary), or allocate field with the size of the active ...
Definition: MMA.C:443
void updateRho()
Update rho value if needed.
Definition: MMA.C:1083
bool variableRho_
Change rho constants in each iteration?
Definition: MMA.H:299
A class for handling words, derived from Foam::string.
Definition: word.H:63
const scalarField & getRho() const
Get rho value if needed.
Definition: MMA.C:1112
tmp< scalarField > gConstr(const scalarField &vars)
g of all constraint functions
Definition: MMA.C:341
scalar z_
Second term in the approximation function.
Definition: MMA.H:112
void adjustStep(scalar &step, const scalar value, const scalar update)
Adjust step to satisfy cireteria.
Definition: MMA.C:730
const word & name() const
Name function is needed to disambiguate those inherited from regIOobject and dictionary.
scalarField oldCValues_
Old constraint values.
Definition: MMA.H:100
scalarField x00_
The twice previous design variables. Used to compute new bounds.
Definition: MMA.H:78
label lastNormalisationStep_
Constaint weight after the normalisation.
Definition: MMA.H:344
bool initializeEverySubproblem_
Initialize every subproblem with x = 0.5*(a + b) and reset Lagrange multipliers.
Definition: MMA.H:252
scalar eps_
Infinitesimal quantity.
Definition: MMA.H:227
Update design variables using the Method of Moving Assymptotes. Can handle inequality constraints...
Definition: MMA.H:61
An Ostream is an abstract base class for all output systems (streams, files, token lists...
Definition: Ostream.H:56
scalar deltaZ_
Definition: MMA.H:212
scalar maxInitRhoMult_
Multiplier of the mean derivative used for the initialisation of rho.
Definition: MMA.H:289
bool dynamicRhoInitialisation_
Change rho constants in each iteration?
Definition: MMA.H:304
OBJstream os(runTime.globalPath()/outputName)
mesh update()
scalarField deltaS_
Definition: MMA.H:215
labelList f(nPoints)
scalarField deltaEta_
Definition: MMA.H:218
scalar raa0_
Constant in p, q functions.
Definition: MMA.H:280
bool boundRho_
Bound the rho value with an upper value?
Definition: MMA.H:169
scalarField a_
Lower design variables constraints.
Definition: MMA.H:152
scalar maxRhoMult_
Multiplier for the max. rho value during its update.
Definition: MMA.H:294
scalarField deltaLamda_
Definition: MMA.H:211
tmp< scalarField > computeResiduals()
Compute and return residuals based on the current solution.
Definition: MMA.C:757
scalarField c_
y multipliers in the objective function
Definition: MMA.H:132
scalarField xNew_
The set of design variables being updated during the subproblem.
Definition: MMA.H:86
A list of pointers to objects of type <T>, with allocation/deallocation management of the pointers...
Definition: List.H:55
void updateSizes()
Update sizes of fields related to the active design variables.
Definition: MMA.C:48
Mesh data needed to do the Finite Volume discretisation.
Definition: fvMesh.H:78
scalar lineSearch()
Perform line search and return max residual corresponding to the updated solution.
Definition: MMA.C:626
const PtrList< scalarField > & getValuesAndApproximations() const
Get objective/constraint values and their approximations.
Definition: MMA.C:1077
scalar cw_
Constaint weight after the normalisation.
Definition: MMA.H:339
void zeroUpdates()
Zero the updates computed in the previous optimisation cycle.
Definition: MMA.C:407
void initializeRho()
Initialize rho constants in the (p, q) functions.
Definition: MMA.C:69
scalar dynamicRhoMult_
The rho values obtained by the dynamic rho initialisation might be too conservative. Multiply with this number to relax them.
Definition: MMA.H:311
scalar move_
Movement of the unatainable upper and lower bounds.
Definition: MMA.H:275
scalar alpha0_
Term multiplying z in the objective function.
Definition: MMA.H:117
scalarField upper_
Upper design variables asymptotes.
Definition: MMA.H:147
label maxLineSearchIters_
Maxmimum number of line search iterations for each iteration of the subproblem.
Definition: MMA.H:238
scalarField Eta_
Lagrange multipliers for the upper limits constraints.
Definition: MMA.H:191
scalarField y_
y in the constraints functions
Definition: MMA.H:127
scalar zeta_
Lagrange multiplier for the z constraint.
Definition: MMA.H:201
A class for managing temporary objects.
Definition: HashPtrTable.H:50
TypeName("MMA")
Runtime type information.
void updateBounds()
Update the bounds associated with the design variables.
Definition: MMA.C:176
bool continuousNormalisation_
Perform the normalisation in each optimisation cycle.
Definition: MMA.H:324
void initialize()
Allocate fields related to constraints.
Definition: MMA.C:215
void storeOldValues()
Store old objcective and constraint values.
Definition: MMA.C:249
Namespace for OpenFOAM.
scalar fTilda(const scalarField &xInit, const scalarField &x, const scalar f, const scalarField &dfdx, const scalar rho)
Computation of the approximate function.
Definition: MMA.C:422
scalarField x0_
The previous design variables. Used to compute new bounds.
Definition: MMA.H:73
scalar oldObjectiveValue_
Old objective value.
Definition: MMA.H:93
static constexpr const zero Zero
Global zero (0)
Definition: zero.H:127
scalarField deltaMu_
Definition: MMA.H:217
bool normalise_
Perform the normalisation.
Definition: MMA.H:319