1 #include <petsc/private/taoimpl.h> /*I "petsctao.h" I*/
2 
3 /*@
4   TaoSetVariableBounds - Sets the upper and lower bounds
5 
6   Logically collective on Tao
7 
8   Input Parameters:
9 + tao - the Tao context
10 . XL  - vector of lower bounds
11 - XU  - vector of upper bounds
12 
13   Level: beginner
14 
15 .seealso: TaoSetObjectiveRoutine(), TaoSetHessianRoutine() TaoSetObjectiveAndGradientRoutine()
16 @*/
17 
TaoSetVariableBounds(Tao tao,Vec XL,Vec XU)18 PetscErrorCode TaoSetVariableBounds(Tao tao, Vec XL, Vec XU)
19 {
20   PetscErrorCode ierr;
21 
22   PetscFunctionBegin;
23   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
24   if (XL) {
25     PetscValidHeaderSpecific(XL,VEC_CLASSID,2);
26     PetscObjectReference((PetscObject)XL);
27   }
28   if (XU) {
29     PetscValidHeaderSpecific(XU,VEC_CLASSID,3);
30     PetscObjectReference((PetscObject)XU);
31   }
32   ierr = VecDestroy(&tao->XL);CHKERRQ(ierr);
33   ierr = VecDestroy(&tao->XU);CHKERRQ(ierr);
34   tao->XL = XL;
35   tao->XU = XU;
36   tao->bounded = PETSC_TRUE;
37   PetscFunctionReturn(0);
38 }
39 
40 /*@C
41   TaoSetVariableBoundsRoutine - Sets a function to be used to compute variable bounds
42 
43   Logically collective on Tao
44 
45   Input Parameters:
46 + tao - the Tao context
47 . func - the bounds computation routine
48 - ctx - [optional] user-defined context for private data for the bounds computation (may be NULL)
49 
50   Calling sequence of func:
51 $      func (Tao tao, Vec xl, Vec xu);
52 
53 + tao - the Tao
54 . xl  - vector of lower bounds
55 . xu  - vector of upper bounds
56 - ctx - the (optional) user-defined function context
57 
58   Level: beginner
59 
60 .seealso: TaoSetObjectiveRoutine(), TaoSetHessianRoutine() TaoSetObjectiveAndGradientRoutine(), TaoSetVariableBounds()
61 
62 Note: The func passed in to TaoSetVariableBoundsRoutine() takes
63 precedence over any values set in TaoSetVariableBounds().
64 
65 @*/
TaoSetVariableBoundsRoutine(Tao tao,PetscErrorCode (* func)(Tao,Vec,Vec,void *),void * ctx)66 PetscErrorCode TaoSetVariableBoundsRoutine(Tao tao, PetscErrorCode (*func)(Tao, Vec, Vec, void*), void *ctx)
67 {
68   PetscFunctionBegin;
69   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
70   tao->user_boundsP = ctx;
71   tao->ops->computebounds = func;
72   tao->bounded = PETSC_TRUE;
73   PetscFunctionReturn(0);
74 }
75 
TaoGetVariableBounds(Tao tao,Vec * XL,Vec * XU)76 PetscErrorCode TaoGetVariableBounds(Tao tao, Vec *XL, Vec *XU)
77 {
78   PetscFunctionBegin;
79   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
80   if (XL) {
81     *XL=tao->XL;
82   }
83   if (XU) {
84     *XU=tao->XU;
85   }
86   PetscFunctionReturn(0);
87 }
88 
89 /*@C
90    TaoComputeVariableBounds - Compute the variable bounds using the
91    routine set by TaoSetVariableBoundsRoutine().
92 
93    Collective on Tao
94 
95    Input Parameters:
96 .  tao - the Tao context
97 
98    Level: developer
99 
100 .seealso: TaoSetVariableBoundsRoutine(), TaoSetVariableBounds()
101 @*/
102 
TaoComputeVariableBounds(Tao tao)103 PetscErrorCode TaoComputeVariableBounds(Tao tao)
104 {
105   PetscErrorCode ierr;
106 
107   PetscFunctionBegin;
108   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
109   PetscStackPush("Tao compute variable bounds");
110   if (!tao->XL || !tao->XU) {
111     if (!tao->solution) SETERRQ(PetscObjectComm((PetscObject)tao),PETSC_ERR_ORDER,"TaoSetInitialVector must be called before TaoComputeVariableBounds");
112     ierr = VecDuplicate(tao->solution, &tao->XL);CHKERRQ(ierr);
113     ierr = VecSet(tao->XL, PETSC_NINFINITY);CHKERRQ(ierr);
114     ierr = VecDuplicate(tao->solution, &tao->XU);CHKERRQ(ierr);
115     ierr = VecSet(tao->XU, PETSC_INFINITY);CHKERRQ(ierr);
116   }
117   if (tao->ops->computebounds) {
118     ierr = (*tao->ops->computebounds)(tao,tao->XL,tao->XU,tao->user_boundsP);CHKERRQ(ierr);
119   }
120   PetscStackPop;
121   PetscFunctionReturn(0);
122 }
123 
124 /*@
125   TaoSetInequalityBounds - Sets the upper and lower bounds
126 
127   Logically collective on Tao
128 
129   Input Parameters:
130 + tao - the Tao context
131 . IL  - vector of lower bounds
132 - IU  - vector of upper bounds
133 
134   Level: beginner
135 
136 .seealso: TaoSetObjectiveRoutine(), TaoSetHessianRoutine() TaoSetObjectiveAndGradientRoutine()
137 @*/
138 
TaoSetInequalityBounds(Tao tao,Vec IL,Vec IU)139 PetscErrorCode TaoSetInequalityBounds(Tao tao, Vec IL, Vec IU)
140 {
141   PetscErrorCode ierr;
142 
143   PetscFunctionBegin;
144   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
145   if (IL) {
146     PetscValidHeaderSpecific(IL,VEC_CLASSID,2);
147     PetscObjectReference((PetscObject)IL);
148   }
149   if (IU) {
150     PetscValidHeaderSpecific(IU,VEC_CLASSID,3);
151     PetscObjectReference((PetscObject)IU);
152   }
153   ierr = VecDestroy(&tao->IL);CHKERRQ(ierr);
154   ierr = VecDestroy(&tao->IU);CHKERRQ(ierr);
155   tao->IL = IL;
156   tao->IU = IU;
157   PetscFunctionReturn(0);
158 }
159 
160 
TaoGetInequalityBounds(Tao tao,Vec * IL,Vec * IU)161 PetscErrorCode TaoGetInequalityBounds(Tao tao, Vec *IL, Vec *IU)
162 {
163   PetscFunctionBegin;
164   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
165   if (IL) {
166     *IL=tao->IL;
167   }
168   if (IU) {
169     *IU=tao->IU;
170   }
171   PetscFunctionReturn(0);
172 }
173 
174 /*@C
175    TaoComputeConstraints - Compute the variable bounds using the
176    routine set by TaoSetConstraintsRoutine().
177 
178    Collective on Tao
179 
180    Input Parameters:
181 .  tao - the Tao context
182 
183    Level: developer
184 
185 .seealso: TaoSetConstraintsRoutine(), TaoComputeJacobian()
186 @*/
187 
TaoComputeConstraints(Tao tao,Vec X,Vec C)188 PetscErrorCode TaoComputeConstraints(Tao tao, Vec X, Vec C)
189 {
190   PetscErrorCode ierr;
191 
192   PetscFunctionBegin;
193   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
194   PetscValidHeaderSpecific(X,VEC_CLASSID,2);
195   PetscValidHeaderSpecific(C,VEC_CLASSID,2);
196   PetscCheckSameComm(tao,1,X,2);
197   PetscCheckSameComm(tao,1,C,3);
198 
199   if (!tao->ops->computeconstraints) SETERRQ(PetscObjectComm((PetscObject)tao),PETSC_ERR_ARG_WRONGSTATE,"TaoSetConstraintsRoutine() has not been called");
200   if (!tao->solution) SETERRQ(PetscObjectComm((PetscObject)tao),PETSC_ERR_ARG_WRONGSTATE,"TaoSetInitialVector must be called before TaoComputeConstraints");
201   ierr = PetscLogEventBegin(TAO_ConstraintsEval,tao,X,C,NULL);CHKERRQ(ierr);
202   PetscStackPush("Tao constraints evaluation routine");
203   ierr = (*tao->ops->computeconstraints)(tao,X,C,tao->user_conP);CHKERRQ(ierr);
204   PetscStackPop;
205   ierr = PetscLogEventEnd(TAO_ConstraintsEval,tao,X,C,NULL);CHKERRQ(ierr);
206   tao->nconstraints++;
207   PetscFunctionReturn(0);
208 }
209 
210 /*@C
211   TaoSetConstraintsRoutine - Sets a function to be used to compute constraints.  TAO only handles constraints under certain conditions, see manual for details
212 
213   Logically collective on Tao
214 
215   Input Parameters:
216 + tao - the Tao context
217 . c   - A vector that will be used to store constraint evaluation
218 . func - the bounds computation routine
219 - ctx - [optional] user-defined context for private data for the constraints computation (may be NULL)
220 
221   Calling sequence of func:
222 $      func (Tao tao, Vec x, Vec c, void *ctx);
223 
224 + tao - the Tao
225 . x   - point to evaluate constraints
226 . c   - vector constraints evaluated at x
227 - ctx - the (optional) user-defined function context
228 
229   Level: intermediate
230 
231 .seealso: TaoSetObjectiveRoutine(), TaoSetHessianRoutine() TaoSetObjectiveAndGradientRoutine(), TaoSetVariablevBounds()
232 
233 @*/
TaoSetConstraintsRoutine(Tao tao,Vec c,PetscErrorCode (* func)(Tao,Vec,Vec,void *),void * ctx)234 PetscErrorCode TaoSetConstraintsRoutine(Tao tao, Vec c, PetscErrorCode (*func)(Tao, Vec, Vec, void*), void *ctx)
235 {
236     PetscFunctionBegin;
237     PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
238     tao->constrained = PETSC_TRUE;
239     tao->constraints = c;
240     tao->user_conP = ctx;
241     tao->ops->computeconstraints = func;
242     PetscFunctionReturn(0);
243 }
244 
245 /*@
246   TaoComputeDualVariables - Computes the dual vectors corresponding to the bounds
247   of the variables
248 
249   Collective on Tao
250 
251   Input Parameters:
252 . tao - the Tao context
253 
254   Output Parameter:
255 + DL - dual variable vector for the lower bounds
256 - DU - dual variable vector for the upper bounds
257 
258   Level: advanced
259 
260   Note:
261   DL and DU should be created before calling this routine.  If calling
262   this routine after using an unconstrained solver, DL and DU are set to all
263   zeros.
264 
265   Level: advanced
266 
267 .seealso: TaoComputeObjective(), TaoSetVariableBounds()
268 @*/
TaoComputeDualVariables(Tao tao,Vec DL,Vec DU)269 PetscErrorCode TaoComputeDualVariables(Tao tao, Vec DL, Vec DU)
270 {
271   PetscErrorCode ierr;
272   PetscFunctionBegin;
273   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
274   PetscValidHeaderSpecific(DL,VEC_CLASSID,2);
275   PetscValidHeaderSpecific(DU,VEC_CLASSID,2);
276   PetscCheckSameComm(tao,1,DL,2);
277   PetscCheckSameComm(tao,1,DU,3);
278   if (tao->ops->computedual) {
279     ierr = (*tao->ops->computedual)(tao,DL,DU);CHKERRQ(ierr);
280   }  else {
281     ierr = VecSet(DL,0.0);CHKERRQ(ierr);
282     ierr = VecSet(DU,0.0);CHKERRQ(ierr);
283   }
284   PetscFunctionReturn(0);
285 }
286 
287 /*@
288   TaoGetDualVariables - Gets pointers to the dual vectors
289 
290   Collective on Tao
291 
292   Input Parameters:
293 . tao - the Tao context
294 
295   Output Parameter:
296 + DE - dual variable vector for the lower bounds
297 - DI - dual variable vector for the upper bounds
298 
299   Level: advanced
300 
301 .seealso: TaoComputeDualVariables()
302 @*/
TaoGetDualVariables(Tao tao,Vec * DE,Vec * DI)303 PetscErrorCode TaoGetDualVariables(Tao tao, Vec *DE, Vec *DI)
304 {
305   PetscFunctionBegin;
306   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
307   if (DE) {
308     *DE = tao->DE;
309   }
310   if (DI) {
311     *DI = tao->DI;
312   }
313   PetscFunctionReturn(0);
314 }
315 
316 /*@C
317   TaoSetEqualityConstraintsRoutine - Sets a function to be used to compute constraints.  TAO only handles constraints under certain conditions, see manual for details
318 
319   Logically collective on Tao
320 
321   Input Parameters:
322 + tao - the Tao context
323 . ce   - A vector that will be used to store equality constraint evaluation
324 . func - the bounds computation routine
325 - ctx - [optional] user-defined context for private data for the equality constraints computation (may be NULL)
326 
327   Calling sequence of func:
328 $      func (Tao tao, Vec x, Vec ce, void *ctx);
329 
330 + tao - the Tao
331 . x   - point to evaluate equality constraints
332 . ce   - vector of equality constraints evaluated at x
333 - ctx - the (optional) user-defined function context
334 
335   Level: intermediate
336 
337 .seealso: TaoSetObjectiveRoutine(), TaoSetHessianRoutine() TaoSetObjectiveAndGradientRoutine(), TaoSetVariableBounds()
338 
339 @*/
TaoSetEqualityConstraintsRoutine(Tao tao,Vec ce,PetscErrorCode (* func)(Tao,Vec,Vec,void *),void * ctx)340 PetscErrorCode TaoSetEqualityConstraintsRoutine(Tao tao, Vec ce, PetscErrorCode (*func)(Tao, Vec, Vec, void*), void *ctx)
341 {
342   PetscErrorCode ierr;
343 
344   PetscFunctionBegin;
345   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
346   if (ce) {
347     PetscValidHeaderSpecific(ce,VEC_CLASSID,2);
348     PetscObjectReference((PetscObject)ce);
349   }
350   ierr = VecDestroy(&tao->constraints_equality);CHKERRQ(ierr);
351 
352   tao->constraints_equality = ce;
353   tao->user_con_equalityP = ctx;
354   tao->ops->computeequalityconstraints = func;
355   PetscFunctionReturn(0);
356 }
357 
358 
359 /*@C
360   TaoSetInequalityConstraintsRoutine - Sets a function to be used to compute constraints.  TAO only handles constraints under certain conditions, see manual for details
361 
362   Logically collective on Tao
363 
364   Input Parameters:
365 + tao - the Tao context
366 . ci   - A vector that will be used to store inequality constraint evaluation
367 . func - the bounds computation routine
368 - ctx - [optional] user-defined context for private data for the inequality constraints computation (may be NULL)
369 
370   Calling sequence of func:
371 $      func (Tao tao, Vec x, Vec ci, void *ctx);
372 
373 + tao - the Tao
374 . x   - point to evaluate inequality constraints
375 . ci   - vector of inequality constraints evaluated at x
376 - ctx - the (optional) user-defined function context
377 
378   Level: intermediate
379 
380 .seealso: TaoSetObjectiveRoutine(), TaoSetHessianRoutine() TaoSetObjectiveAndGradientRoutine(), TaoSetVariableBounds()
381 
382 @*/
TaoSetInequalityConstraintsRoutine(Tao tao,Vec ci,PetscErrorCode (* func)(Tao,Vec,Vec,void *),void * ctx)383 PetscErrorCode TaoSetInequalityConstraintsRoutine(Tao tao, Vec ci, PetscErrorCode (*func)(Tao, Vec, Vec, void*), void *ctx)
384 {
385   PetscErrorCode ierr;
386 
387   PetscFunctionBegin;
388   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
389   if (ci) {
390     PetscValidHeaderSpecific(ci,VEC_CLASSID,2);
391     PetscObjectReference((PetscObject)ci);
392   }
393   ierr = VecDestroy(&tao->constraints_inequality);CHKERRQ(ierr);
394   tao->constraints_inequality = ci;
395 
396   tao->user_con_inequalityP = ctx;
397   tao->ops->computeinequalityconstraints = func;
398   PetscFunctionReturn(0);
399 }
400 
401 
402 /*@C
403    TaoComputeEqualityConstraints - Compute the variable bounds using the
404    routine set by TaoSetEqualityConstraintsRoutine().
405 
406    Collective on Tao
407 
408    Input Parameters:
409 .  tao - the Tao context
410 
411    Level: developer
412 
413 .seealso: TaoSetEqualityConstraintsRoutine(), TaoComputeJacobianEquality()
414 @*/
415 
TaoComputeEqualityConstraints(Tao tao,Vec X,Vec CE)416 PetscErrorCode TaoComputeEqualityConstraints(Tao tao, Vec X, Vec CE)
417 {
418   PetscErrorCode ierr;
419 
420   PetscFunctionBegin;
421   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
422   PetscValidHeaderSpecific(X,VEC_CLASSID,2);
423   PetscValidHeaderSpecific(CE,VEC_CLASSID,2);
424   PetscCheckSameComm(tao,1,X,2);
425   PetscCheckSameComm(tao,1,CE,3);
426 
427   if (!tao->ops->computeequalityconstraints) SETERRQ(PetscObjectComm((PetscObject)tao),PETSC_ERR_ARG_WRONGSTATE,"TaoSetEqualityConstraintsRoutine() has not been called");
428   if (!tao->solution) SETERRQ(PetscObjectComm((PetscObject)tao),PETSC_ERR_ARG_WRONGSTATE,"TaoSetInitialVector must be called before TaoComputeEqualityConstraints");
429   ierr = PetscLogEventBegin(TAO_ConstraintsEval,tao,X,CE,NULL);CHKERRQ(ierr);
430   PetscStackPush("Tao equality constraints evaluation routine");
431   ierr = (*tao->ops->computeequalityconstraints)(tao,X,CE,tao->user_con_equalityP);CHKERRQ(ierr);
432   PetscStackPop;
433   ierr = PetscLogEventEnd(TAO_ConstraintsEval,tao,X,CE,NULL);CHKERRQ(ierr);
434   tao->nconstraints++;
435   PetscFunctionReturn(0);
436 }
437 
438 
439 /*@C
440    TaoComputeInequalityConstraints - Compute the variable bounds using the
441    routine set by TaoSetInequalityConstraintsRoutine().
442 
443    Collective on Tao
444 
445    Input Parameters:
446 .  tao - the Tao context
447 
448    Level: developer
449 
450 .seealso: TaoSetInequalityConstraintsRoutine(), TaoComputeJacobianInequality()
451 @*/
452 
TaoComputeInequalityConstraints(Tao tao,Vec X,Vec CI)453 PetscErrorCode TaoComputeInequalityConstraints(Tao tao, Vec X, Vec CI)
454 {
455   PetscErrorCode ierr;
456 
457   PetscFunctionBegin;
458   PetscValidHeaderSpecific(tao,TAO_CLASSID,1);
459   PetscValidHeaderSpecific(X,VEC_CLASSID,2);
460   PetscValidHeaderSpecific(CI,VEC_CLASSID,2);
461   PetscCheckSameComm(tao,1,X,2);
462   PetscCheckSameComm(tao,1,CI,3);
463 
464   if (!tao->ops->computeinequalityconstraints) SETERRQ(PetscObjectComm((PetscObject)tao),PETSC_ERR_ARG_WRONGSTATE,"TaoSetInequalityConstraintsRoutine() has not been called");
465   if (!tao->solution) SETERRQ(PetscObjectComm((PetscObject)tao),PETSC_ERR_ARG_WRONGSTATE,"TaoSetInitialVector must be called before TaoComputeInequalityConstraints");
466   ierr = PetscLogEventBegin(TAO_ConstraintsEval,tao,X,CI,NULL);CHKERRQ(ierr);
467   PetscStackPush("Tao inequality constraints evaluation routine");
468   ierr = (*tao->ops->computeinequalityconstraints)(tao,X,CI,tao->user_con_inequalityP);CHKERRQ(ierr);
469   PetscStackPop;
470   ierr = PetscLogEventEnd(TAO_ConstraintsEval,tao,X,CI,NULL);CHKERRQ(ierr);
471   tao->nconstraints++;
472   PetscFunctionReturn(0);
473 }
474