Skip to content

Commit a09b32f

Browse files
committed
wip: supporting exact hessian
1 parent b9f325f commit a09b32f

File tree

1 file changed

+17
-3
lines changed

1 file changed

+17
-3
lines changed

src/controller/nonlinmpc.jl

Lines changed: 17 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,7 @@ struct NonLinMPC{
6868
estim::SE, Hp, Hc, nb, weights::CW,
6969
JE::JEfunc, gc!::GCfunc, nc, p::PT,
7070
transcription::TM, optim::JM,
71-
gradient::GB, jacobian::JB, oracle
71+
gradient::GB, jacobian::JB, hessian::HB, oracle
7272
) where {
7373
NT<:Real,
7474
SE<:StateEstimator,
@@ -77,6 +77,7 @@ struct NonLinMPC{
7777
JM<:JuMP.GenericModel,
7878
GB<:AbstractADType,
7979
JB<:AbstractADType,
80+
HB<:Union{AbstractADType, Nothing},
8081
PT<:Any,
8182
JEfunc<:Function,
8283
GCfunc<:Function,
@@ -218,6 +219,8 @@ This controller allocates memory at each time step for the optimization.
218219
function, see [`DifferentiationInterface` doc](@extref DifferentiationInterface List).
219220
- `jacobian=default_jacobian(transcription)` : an `AbstractADType` backend for the Jacobian
220221
of the nonlinear constraints, see `gradient` above for the options (default in Extended Help).
222+
- `hessian=false` : an `AbstractADType` backend for the Hessian of the Lagrangian, see
223+
`gradient` above for the options (`false` to skip it and use `optim` approximation).
221224
- `oracle=JuMP.solver_name(optim)=="Ipopt"`: use the efficient [`VectorNonlinearOracle`](@extref MathOptInterface MathOptInterface.VectorNonlinearOracle)
222225
for the nonlinear constraints (not supported by most optimizers for now).
223226
- additional keyword arguments are passed to [`UnscentedKalmanFilter`](@ref) constructor
@@ -314,14 +317,15 @@ function NonLinMPC(
314317
optim::JuMP.GenericModel = JuMP.Model(DEFAULT_NONLINMPC_OPTIMIZER, add_bridges=false),
315318
gradient::AbstractADType = DEFAULT_NONLINMPC_GRADIENT,
316319
jacobian::AbstractADType = default_jacobian(transcription),
320+
hessian::Union{AbstractADType, Bool, Nothing} = false,
317321
oracle::Bool = JuMP.solver_name(optim)=="Ipopt",
318322
kwargs...
319323
)
320324
estim = default_estimator(model; kwargs...)
321325
return NonLinMPC(
322326
estim;
323327
Hp, Hc, Mwt, Nwt, Lwt, Cwt, Ewt, JE, gc, nc, p, M_Hp, N_Hc, L_Hp,
324-
transcription, optim, gradient, jacobian, oracle
328+
transcription, optim, gradient, jacobian, hessian, oracle
325329
)
326330
end
327331

@@ -379,6 +383,7 @@ function NonLinMPC(
379383
optim::JuMP.GenericModel = JuMP.Model(DEFAULT_NONLINMPC_OPTIMIZER, add_bridges=false),
380384
gradient::AbstractADType = DEFAULT_NONLINMPC_GRADIENT,
381385
jacobian::AbstractADType = default_jacobian(transcription),
386+
hessian::Union{AbstractADType, Bool, Nothing} = false,
382387
oracle::Bool = JuMP.solver_name(optim)=="Ipopt"
383388
) where {
384389
NT<:Real,
@@ -394,15 +399,24 @@ function NonLinMPC(
394399
validate_JE(NT, JE)
395400
gc! = get_mutating_gc(NT, gc)
396401
weights = ControllerWeights(estim.model, Hp, Hc, M_Hp, N_Hc, L_Hp, Cwt, Ewt)
402+
hessian = default_hessian(gradient, jacobian, hessian)
397403
return NonLinMPC{NT}(
398404
estim, Hp, Hc, nb, weights, JE, gc!, nc, p,
399-
transcription, optim, gradient, jacobian, oracle
405+
transcription, optim, gradient, jacobian, hessian, oracle
400406
)
401407
end
402408

403409
default_jacobian(::SingleShooting) = DEFAULT_NONLINMPC_JACDENSE
404410
default_jacobian(::TranscriptionMethod) = DEFAULT_NONLINMPC_JACSPARSE
405411

412+
function default_hessian(gradient, jacobian, hessian::Bool)
413+
if hessian
414+
return DEFAULT_NONLINMPC_HESSIAN
415+
else
416+
return nothing
417+
end
418+
end
419+
406420
"""
407421
validate_JE(NT, JE) -> nothing
408422

0 commit comments

Comments
 (0)