-
Notifications
You must be signed in to change notification settings - Fork 1
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
added: multiple shooting transcription for LinMPC
and NonLinMPC
#155
Conversation
but not `NonLinModel` for now
adding standard library dependencies in them
Codecov ReportAttention: Patch coverage is
Additional details and impacted files@@ Coverage Diff @@
## main #155 +/- ##
==========================================
- Coverage 99.02% 96.29% -2.74%
==========================================
Files 24 25 +1
Lines 3790 4017 +227
==========================================
+ Hits 3753 3868 +115
- Misses 37 149 +112 ☔ View full report in Codecov by Sentry. |
… of cost function
to save some computation during `NonLinMPC` optimization
LinMPC
and NonLinMPC
LinMPC
and NonLinMPC
@baggepinnen I'm curious, do you know any paper that compares a single direct shooting transcription to a multiple shooting one in the context of MPC ? It seems that everyone is saying "It scales better" but no one really prove it lol. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do you notice any performance and/or convergence benefit from this new transcription?
There does not appear to be any tests?
Edit: I noticed now that some test had been added after I initiated the review yesterday
```math | ||
\mathbf{Z} = \begin{bmatrix} \mathbf{ΔU} \\ \mathbf{X̂_0} \end{bmatrix} | ||
``` | ||
thus it also includes the predicted states, expressed as deviation vectors from the |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
expressed as deviation vectors from the operating point
is this the case also for nonlinear MPC?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, that's also the case for nonlinear MPC. This allows NonLinModel
with nonzero operating points, for example:
using Plots, ModelPredictiveControl, ControlSystemsBase
model1 = setop!(LinModel(tf(5, [10, 1]), 0.5), uop=[50], yop=[30])
f!(xnext,x,u,_,p) = (xnext .= p.A*x + p.B*u)
h!(y,x,_,p) = (y .= p.C*x)
p = (;A=model1.A, B=model1.Bu, C=model1.C)
model2 = NonLinModel(f!, h!, model1.Ts, 1, 1, 1; p, solver=nothing)
model2 = setop!(model2, uop=[50], yop=[30])
mpc = NonLinMPC(model2, Hp=10, transcription=MultipleShooting())
sim!(mpc, 100, x_0=[0], x̂_0=[0, 0]) |> plot
and it will work exactly like a linear MPC:
mpclinear = LinMPC(model1, Hp=10, transcription=MultipleShooting())
sim!(mpclinear, 100, x_0=[0], x̂_0=[0, 0]) |> plot
It's useful for the tests, maybe not so for real life applications. 🤔
edit: maybe useful for really simple empirical but nonlinear model, e.g. models with
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Tagging you since you are probably not notified since the PR is merged @baggepinnen
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Will add a short comment on that in the docstring
I don't have a reference in mind, but it aligns very well with my own experience. The scaling is not the primary benefit, it's the convergence behavior. Getting single shooting without feedback (like in iLQG) to converge to a reasonable optimum is hopeless for many problems that multiple shooting handles effortlessly. |
Thanks for the review, I'll apply them in the next PR! Ok I see, I just did not come across problems in which convergence is really hard with a single shooting transcription. edit: FYI, I tested it on the unstable pendulum model of the manual, and it's about 5-6 times slower than the single shooting transcription. I discuss a little bit more in details my hypothesis of why on the discourse post. |
I ran some additional tests on the inverted pendulum. My example in the manual uses a control horizon of Now, If I chose |
Are you computing dense Jacobians with ForwardDiff? If so, that requires |
Yes, all the AD computations are dense right now in the package. That's what That's why I plan to integrate |
@baggepinnen I will probably finish the multiple shooting transcription soon.
LinMPC
works well, still missing some work forNonLinMPC
The documentation is ready for a quick revision, do you see any mistake or something that is not clear in the docstring of
LinMPC
,NonLinMPC
,TranscriptionMethod
,SingleShooting
andMultipleShooting
, here (there are only minor changes inLinMPC
andNonLinMPC
docstring):https://juliacontrol.github.io/ModelPredictiveControl.jl/previews/PR155
There is also the internal
init_defectmat
that you can look quickly, for linear plant models.P.S. Multiple dispatch is so powerful! Now I dispatch on the type of the plant model, the predictive controller, the transcription method and the state estimator sometimes.