ctl.ControlSBML
¶
controlSBML
provides ways to use an SBML model to construct an
object representing a system
model that can be used by the control
package.
Two kinds of control
objects can be constructed.
The first,
control.NonlinearIOSystem
,
wraps an entire nonlinear SBML model.
This allows the control
package to do the same kind of detailed
simulations that are provided by SBML simulators as as libroadrunner
and Copasi
.
The second object,
control.StateSpace
, provides a linear approximation to the SBML model.
control.NonlinearIOSystem
and
control.StateSpace
objects are constructed from an
ctl.ControlSBML
object.
In the sequel, we use the following Antiimony representation of an SBML model.
1SIMPLE_MODEL = """
2 species E1;
3 J1: S1 -> S2; S1 + E1
4 S1 = 10; S2 = 0; E1 = 1;
5"""
Constructors¶
We begin with constructing a ctl.ControlSBML
object.
This requires having a representation of an SBML model.
This can be an XML file, an XML URL, an antimony file,
or a libroadrunner
object.
We refer to any of these representations of the SBML model as
a model reference.
The following constructs ctl.ControlSBML
object for this model.
ctlsb = ctl.ControlSBML(SIMPLE_MODEL)
This object has a number of useful properties.
ctlsb.antimony
is the Antimony string that corresponds to the model reference in the constructor.ctlsb.roadrunner
is thelibroadrunner
object for the model reference in the constructor.ctlsb.state_ser
is apandas
Series
that provides the values of the concentrations of floating species (the state variables).ctlsb.setTime(time)
runs the simulation from time 0 to a desired time. This updatesctlsb.state_ser
.
To create an object that is more useful for control analysis, you should specify at least one input and at least one output. An input is a chemical species that can be manipulated by increasing or decreasing its value. An output is a chemical species or reaction flux that can be read. An example of this constructor is:
ctlsb = ctl.ControlSBML(SIMPLE_MODEL,
input_names=["E1"], output_names=["S2"])
Note that both input_names
and output_names
are lists of strings.
Inputs and outputs must be specified to make use of
subsequent capabilities of ctl.ControlSBML
.
control.NonlinearIOSystem
¶
The method ctl.ControlSBML.makeNonlinearIOSystem
constructs
a control.NonlinearIOSystem
object for an SBML model.
The control.NonlinearIOSystem
object provides a way to use
many of the capabilities of the control system library.
For example,
ctlsb = ctl.ControlSBML(SIMPLE_MODEL,
input_names=["E1"], output_names=["S1", "S2"])
sys = ctlsb.makeNonlinearIOSystem("simple")
sys
is a control.NonlinearIOSystem
object,
and the following simulates this system for 5 s.
times = [0.1*n for n in range(51)]
time_response = control.input_output_response(sys,
times, X0=ctl.makeStateVector(sys))
ctlsb
is constructed to have the input E1
and the outputs S1
and S2
.
sys
is a control.NonlinearIOSystem
object
that wraps the SBML model.
time_response
is a control.TimeResponseData
object.
The simulation requires knowlege of initial values for all state variables,
which is provided by the method ctl.makeStateVector
.
Going a bit further, we introduce a plotting function for
the control.TimeResponseData
object.
1def plotTimeResponse(time_response, output_names,
2 is_legend=True, stmts=None):
3 # Plots the results of running a simulation
4 outputs = time_response.outputs
5 times = time_response.time
6 colors = ["orange", "green"]
7 for idx in range(len(output_names)):
8 if np.ndim(outputs) > 1:
9 plt.plot(times, outputs[idx,:], c=colors[idx])
10 else:
11 plt.plot(times, outputs, c=colors[idx])
12 if is_legend:
13 _ = plt.legend(output_names)
14 if stmts is None:
15 stmts = []
16 for stmt in stmts:
17 exec(stmt)
18 plt.xlabel("time")
19 plt.ylabel("concentration")
We execute the statement below to plot the simulation results.
plotTimeResponse(time_response, ["S1", "S2"])
control.StateSpace
¶
A state space model is a linear system of differential equations in which there are \(n\) states, \(p\) inputs, and \(q\) outputs.
where:
\({\bf x}\) is the state variable, \({\bf u}\) is the input vector, and \({\bf y}\) is the output.
controlSBML
constructs a control.StateSpace
object for an SBML model as follows.
The state variables are
floating species.
The \({\bf u}\) are names of floating
species that are manipulated inputs (input_names
).
The \({\bf y}\) are the names
of measured outputs (output_names
), either
floating species or names of reactions whose fluxes are output.
A
linear approximation for an SBML model is constructed
using the Jacobian of the state variables at a specified operating point.
The operating point is a simulation time at which state variables are assigned their values
to calculate the Jacobian.
Once a ctl.ControlSBML
object has been constructed,
the method makeStateSpace
is used to create
a control.StateSpace
object.
This is illustrated below to construct a control.StateSpace
object using
time 0 as the operating point.
ctlsb = ctl.ControlSBML(SIMPLE_MODEL,
input_names=["S1"], output_names=["S2"])
state_space = ctlsb.makeStateSpace(time=0)
The resulting state space model is represented below.
\({\bf x}\) is a 3 dimensional vector
that correspond to the state variables (floating species)
E1
, S1
, and S2
.
\(u\) and \(y\) are scalars (and so
are not in bold).
\({\bf A}\) is in the upper left;
\({\bf B}\) is in the upper right;
and \({\bf C}\) is in the lower left.
\({\bf A}\) is A
\(3 \times 3\) matrix;
\({\bf B}\) is a \(3 \times 1\) matrix;
and \({\bf C}\) is \(1 \times 3\).
We can construct a transfer function from a control.StateSpace
object.
The transfer function for the above system is obtained by
transfer_function = control.tf(state_space)
and is displayed as
The DC gain for this transfer function is \(\infty\).
This makes sense since by having
a unti input for times \(\geq 0\) and
a single reaction that consumes S1
to produce S2
,
the output increases without bound.
Now consider a slightly different reaction network.
1model = """
2 J1: S1 -> S2; S1
3 J2: S2 -> S1; S2
4 J3: S2 -> ; k*S2
5 S1 = 10; S2 = 0;
6 k = 0.8
7"""
8
9ctlsb = ctl.ControlSBML(model,
10 input_names=["S1"], output_names=["S2"])
11state_space = ctlsb.makeStateSpace()
The state space matrices are:
We simulate and plot the response of the state space model
to a unit step in the input in S1
.
1times = [0.1*n for n in range(301)]
2ss_time_response = control.forced_response(state_space,
3 times, X0=[10, 0], U=1)
4plotTimeResponse(ss_time_response, ["S2"], is_legend=False)
5plt.plot([0, 30], [1.25, 1.25], linestyle="--")
The transfer function is
and so the DC gain is \(1/0.8=1.25\), which is consistent with the plot.