@@ -50,6 +50,10 @@ namespace ocs2 {
5050
5151namespace {
5252ipm::Settings rectifySettings (const OptimalControlProblem& ocp, ipm::Settings&& settings) {
53+ // We have to create the value function if we want to compute the Lagrange multipliers.
54+ if (settings.computeLagrangeMultipliers ) {
55+ settings.createValueFunction = true ;
56+ }
5357 // True does not make sense if there are no constraints.
5458 if (ocp.equalityConstraintPtr ->empty ()) {
5559 settings.projectStateInputEqualityConstraints = false ;
@@ -463,18 +467,20 @@ IpmSolver::OcpSubproblemSolution IpmSolver::getOCPSolution(const vector_t& delta
463467
464468void IpmSolver::extractValueFunction (const std::vector<AnnotatedTime>& time, const vector_array_t & x, const vector_array_t & lmd,
465469 const vector_array_t & deltaXSol, vector_array_t & deltaLmdSol) {
466- valueFunction_ = hpipmInterface_.getRiccatiCostToGo (dynamics_[0 ], lagrangian_[0 ]);
467- // Compute costate directions
468- deltaLmdSol.resize (deltaXSol.size ());
469- for (int i = 0 ; i < time.size (); ++i) {
470- deltaLmdSol[i] = valueFunction_[i].dfdx ;
471- deltaLmdSol[i].noalias () += valueFunction_[i].dfdxx * x[i];
472- }
473- // Correct for linearization state
474- for (int i = 0 ; i < time.size (); ++i) {
475- valueFunction_[i].dfdx .noalias () -= valueFunction_[i].dfdxx * x[i];
476- if (settings_.computeLagrangeMultipliers ) {
477- valueFunction_[i].dfdx .noalias () += lmd[i];
470+ if (settings_.createValueFunction ) {
471+ valueFunction_ = hpipmInterface_.getRiccatiCostToGo (dynamics_[0 ], lagrangian_[0 ]);
472+ // Compute costate directions
473+ deltaLmdSol.resize (deltaXSol.size ());
474+ for (int i = 0 ; i < time.size (); ++i) {
475+ deltaLmdSol[i] = valueFunction_[i].dfdx ;
476+ deltaLmdSol[i].noalias () += valueFunction_[i].dfdxx * x[i];
477+ }
478+ // Correct for linearization state
479+ for (int i = 0 ; i < time.size (); ++i) {
480+ valueFunction_[i].dfdx .noalias () -= valueFunction_[i].dfdxx * x[i];
481+ if (settings_.computeLagrangeMultipliers ) {
482+ valueFunction_[i].dfdx .noalias () += lmd[i];
483+ }
478484 }
479485 }
480486}
@@ -551,9 +557,7 @@ PerformanceIndex IpmSolver::setupQuadraticSubproblem(const std::vector<Annotated
551557 }
552558
553559 ipm::condenseIneqConstraints (barrierParam, slackStateIneq[i], dualStateIneq[i], stateIneqConstraints_[i], lagrangian_[i]);
554- if (settings_.computeLagrangeMultipliers ) {
555- performance[workerId].dualFeasibilitiesSSE += multiple_shooting::evaluateDualFeasibilities (lagrangian_[i]);
556- }
560+ performance[workerId].dualFeasibilitiesSSE += multiple_shooting::evaluateDualFeasibilities (lagrangian_[i]);
557561 performance[workerId].dualFeasibilitiesSSE +=
558562 ipm::evaluateComplementarySlackness (barrierParam, slackStateIneq[i], dualStateIneq[i]);
559563 } else {
@@ -597,9 +601,7 @@ PerformanceIndex IpmSolver::setupQuadraticSubproblem(const std::vector<Annotated
597601 ipm::condenseIneqConstraints (barrierParam, slackStateIneq[i], dualStateIneq[i], stateIneqConstraints_[i], lagrangian_[i]);
598602 ipm::condenseIneqConstraints (barrierParam, slackStateInputIneq[i], dualStateInputIneq[i], stateInputIneqConstraints_[i],
599603 lagrangian_[i]);
600- if (settings_.computeLagrangeMultipliers ) {
601- performance[workerId].dualFeasibilitiesSSE += multiple_shooting::evaluateDualFeasibilities (lagrangian_[i]);
602- }
604+ performance[workerId].dualFeasibilitiesSSE += multiple_shooting::evaluateDualFeasibilities (lagrangian_[i]);
603605 performance[workerId].dualFeasibilitiesSSE +=
604606 ipm::evaluateComplementarySlackness (barrierParam, slackStateIneq[i], dualStateIneq[i]);
605607 performance[workerId].dualFeasibilitiesSSE +=
@@ -628,9 +630,7 @@ PerformanceIndex IpmSolver::setupQuadraticSubproblem(const std::vector<Annotated
628630 lagrangian_[i] = std::move (result.cost );
629631 }
630632 ipm::condenseIneqConstraints (barrierParam, slackStateIneq[N], dualStateIneq[N], stateIneqConstraints_[N], lagrangian_[N]);
631- if (settings_.computeLagrangeMultipliers ) {
632- performance[workerId].dualFeasibilitiesSSE += multiple_shooting::evaluateDualFeasibilities (lagrangian_[N]);
633- }
633+ performance[workerId].dualFeasibilitiesSSE += multiple_shooting::evaluateDualFeasibilities (lagrangian_[N]);
634634 performance[workerId].dualFeasibilitiesSSE += ipm::evaluateComplementarySlackness (barrierParam, slackStateIneq[N], dualStateIneq[N]);
635635 }
636636 };
0 commit comments