In this section, a simple optimal control problem will be solved. Consider the optimal control problem for the Van der Pol oscillator model:

optimizationVDP_Opt (objective = cost(finalTime), startTime = 0, finalTime = 20)// The statesReal x1(start=0,fixed=true); Real x2(start=1,fixed=true);// The control signalinputReal u; Real cost(start=0,fixed=true);equationder(x1) = (1 - x2^2) * x1 - x2 + u;der(x2) = x1;der(cost) = x1^2 + x2^2 + u^2;constraintu<=0.75;endVDP_Opt;

Create a new file named `VDP_Opt.mop`

and save it in you working directory. Notice that this model contains both the dynamic system to be optimized and the optimization
specification. This is possible since Optimica is an extension of Modelica and thereby supports also Modelica constructs such
as variable declarations and equations. In most cases, however, Modelica models are stored separately from the Optimica specifications.

Next, create a Python script file and a write (or copy paste) the following commands:

# Import the function for compilation of models and the JMUModel classfrompymodelicaimportcompile_jmufrompyjmiimportJMUModel# Import the plotting libraryimportmatplotlib.pyplotasplt

Next, we compile and load the model:

# Compile modeljmu_name = compile_jmu(,"VDP_Opt")"VDP_Opt.mop"# Load modelvdp = JMUModel(jmu_name)

The function `compile_jmu`

invokes the Optimica compiler and compiles the model into a DLL, which is then loaded when the `vdp`

object is created. This object represents the compiled model and is used to invoke the optimization algorithm:

res = vdp.optimize()

In this case, we use the default settings for the optimization algorithm. The result object can now be used to access the optimization result:

# Extract variable profilesx1=res[] x2=res['x1'] u=res['x2'] t=res['u']'time'

The variable trajectories are returned as numpy arrays and can be used for further analysis of the optimization result or for visualization:

plt.figure(1) plt.clf() plt.subplot(311) plt.plot(t,x1) plt.grid() plt.ylabel() plt.subplot(312) plt.plot(t,x2) plt.grid() plt.ylabel('x1') plt.subplot(313) plt.plot(t,u) plt.grid() plt.ylabel('x2') plt.xlabel('u') plt.show()'time'

You should now see the optimization result as shown in Figure 7.1.