Documentation | Build Status | Coverage |
---|---|---|
DynamicNLPModels.jl is a package for Julia designed for representing linear model predictive control (MPC) problems. It includes an API for building a model from user defined data and querying solutions.
To install this package, please use
using Pkg
Pkg.add(url="https://github.com/MadNLP/DynamicNLPModels.jl.git")
or
pkg> add https://github.com/MadNLP/DynamicNLPModels.jl.git
DynamicNLPModels.jl can construct both sparse and condensed formulations for MPC problems based on user defined data. We use the methods discussed by Jerez et al. to eliminate the states and condense the problem. DynamicNLPModels.jl constructs models that are subtypes of AbstractNLPModel
from NLPModels.jl enabling both the sparse and condensed models to be solved with a variety of different solver packages in Julia. DynamicNLPModels was designed in part with the goal of solving linear MPC problems on the GPU. This can be done within MadNLP.jl using MadNLPGPU.jl.
The general sparse formulation used within DynamicNLPModels.jl is
$$\begin{align} \min_{s, u, v} \quad & s_N^\top Q_f sN + \frac{1}{2} \sum{i = 0}^{N-1} \left[ \begin{array}{c} s_i \ u_i \end{array} \right]^\top \left[ \begin{array}{cc} Q & S \ S^\top & R \end{array} \right] \left[ \begin{array}{c} s_i \ ui \end{array} \right]\ \textrm{s.t.} \quad & s{i+1} = As_i + Bu_i + w_i \quad \forall i = 0, 1, \cdots, N - 1 \ & u_i = Ks_i + v_i \quad \forall i = 0, 1, \cdots, N - 1 \ & g^l \le E s_i + F u_i \le g^u \quad \forall i = 0, 1, \cdots, N - 1\ & s^l \le s_i \le s^u \quad \forall i = 0, 1, \cdots, N \ & u^l \le u_i \le u^u \quad \forall i = 0, 1, \cdots, N - 1\ & s_0 = \bar{s} \end{align}$$
where $s_i$ are the states, $u_i$ are the inputs$, $N$ is the time horizon, $\bar{s}$ are the initial states, and $Q$, $R$, $A$, and $B$ are user defined data. The matrices $Q_f$, $S$, $K$, $E$, and $F$ and the vectors $w$, $g^l$, $g^u$, $s^l$, $s^u$, $u^l$, and $u^u$ are optional data. $v_t$ is only needed in the condensed formulation, and it arises when $K$ is defined by the user to ensure numerical stability of the condensed problem.
The condensed formulation used within DynamicNLPModels.jl is
$$\begin{align} \min_{\boldsymbol{v}} \quad & \frac{1}{2} \boldsymbol{v}^\top \boldsymbol{H} \boldsymbol{v} + \boldsymbol{h}^\top \boldsymbol{v} + \boldsymbol{h}_0\ \textrm{s.t.} \quad & d^l \le \boldsymbol{J} \boldsymbol{v} \le d^u. \end{align}$$
DynamicNLPModels.jl takes user defined data to form a SparseLQDyanmicModel
or a DenseLQDynamicModel
. The user can first create an object containing the LQDynamicData
, or they can pass the data directly to the SparseLQDynamicModel
or DenseLQDynamicModel
constructors.
using DynamicNLPModels, Random, LinearAlgebra
Q = 1.5 * Matrix(I, (3, 3))
R = 2.0 * Matrix(I, (2, 2))
A = rand(3, 3)
B = rand(3, 2)
N = 5
s0 = [1.0, 2.0, 3.0]
lqdd = LQDynamicData(s0, A, B, Q, R, N; **kwargs)
sparse_lqdm = SparseLQDynamicModel(lqdd)
dense_lqdm = DenseLQDynamicModel(lqdd)
# or
sparse_lqdm = SparseLQDynamicModel(s0, A, B, Q, R, N; **kwargs)
dense_lqdm = DenseLQDynamicModel(s0, A, B, Q, R, N; **kwargs)
Optional data (such as $s^l$, $s^u$, $S$, or $Q_f$) can be passed as key word arguments. The models sparse_lqdm
or dense_lqdm
can be solved by different solvers such as MadNLP.jl or Ipopt (Ipopt requires the extension NLPModelsIpopt.jl). An example script under \examples
shows how the dense problem can be solved on a GPU using MadNLPGPU.jl.
DynamicNLPModels.jl also includes an API for querying solutions and reseting data. Solutions can be queried using get_u(solver_ref, dynamic_model)
and get_s(solver_ref, dynamic_model)
. The problem can be reset with a new $s_0$ by calling reset_s0!(dynamic_model, s0)
.