How to use parameter optimization in parallel using the Simulink Design Optimization and Global Optimization Toolbox in MATLAB R2016b?

13 views (last 30 days)
I use "ga" from the GO Toolbox for parameter optimization of a Simulink model. For this purpose, a custom fitness function was written, which calls the Simulink model with the estimated parameters and compares the simulation results with reference data to evaluate the goodness of the parameter estimation at each generation with each parameter set (population).
Using the settings:
- UseParallel = false;
- UseVectorized = true;
and the optimization works.
To save computing time, the optimization should be parallelized. But if I only activate UseParallel
- UseParallel = true;
- UseVectorized = true;
and change the for-loop in the fitness function for the evaluation of the single parameter sets to a parfor-loop, I get the following error:
Error using sdo.SimulationTest/sim (line 612)
Invalid setting in 'HvacModelLibTestEV24_2/10' for parameter 'Value'.
Error using sdo.SimulationTest/sim (line 612)
Error evaluating parameter 'Value' in 'HvacModelLibTestEV24_2/10'
Error using sdo.SimulationTest/sim (line 612)
Undefined function or variable 'DEF'.
...

Accepted Answer

MathWorks Support Team
MathWorks Support Team on 29 Jun 2023
Edited: MathWorks Support Team on 4 Oct 2021
You currently use some Simulink Designe Optimization (SDO) "helper" functions and mix them with calls to the ga() function that comes from the Global Optimization (GO) toolbox. This works because the infrastructure allows such optimization to be performed without parallelization.
However, if you want to use the Parallel Computing Toolbox, it only accepts certain workflows, where the SDO and GO Toolbox are considered separate from each other and cannot be combined. 
These workflows can be found in the following documentation links:
The SDO Toolbox supports parallelization of parameter estimation using "sdo.optimize" using the following methods:
"Parameter Estimator and sdo.optimize to estimate parameters using the fmincon, lsqnonlin, and patternsearch methods"
https://www.mathworks.com/help/sldo/ug/how-to-use-parallel-computing-gui_bs2zam4-1.html
The GO Toolbox directly uses the main solver for parameter estimation. The corresponding workflow is described in the following link:
https://www.mathworks.com/help/gads/how-to-use-parallel-processing.html
In your workflow, you want to run multiple simulations where the parameters change their values and should be optimized. Therefore, the following workflow, within GO Toolbox, would apply here, using the "Simulink.SimulationInput class" using "parsim":
https://www.mathworks.com/matlabcentral/answers/595402-how-to-use-the-parallel-computing-toolbox-of-matlab-to-optimize-the-parameters-of-a-simulink-model-w
First, you should enable the "UseVectorized" option and disable the "UseParallel" option in the GA optimization options. This means that we will pass the entire population to our objective function. 
Once our target function has the parameters for the entire population, we can create an array of Simulink.SimulationInput objects for each member of the population. 
Then we can call "parsim" with this array of input objects. This means that each "generation" runs serially, but we can run the cost function in parallel for all members of the population of a single generation. The generations have to be run serially anyway to transfer the information from one generation to the next, so this is the maximum parallelization you can hope for. 
By default, the following example shows the workflow for how to use "parsim" for "ga":
fitness = myFitnessFunc(generation)
[populationSize,nvars] = size(generation);
in(1:populationSize) = Simulink.SimulationInput(model);
for i=1:populationSize
    in(i) = in(i).setModelParameter('SimulationMode', 'rapid');
    in(i) = in(i).setModelParameter('RapidAcceleratorUpToDateCheck', 'off');
    in(i) = in(i).setVariable('myVar', generation(1));
    in(i) = in(i).setVariable('myVar2', generation(2));
end
out = parsim(in);
fitness = %some post processing, could even do in a postSim callback 
end
 
solution = ga(@myObjectiveFunc,populationSize);
In addition, it looks like you want to use "RapidAcceleratorUpToDateCheck" - off. This option is equivalent to using "Fast Restart" in Normal or Accelerator mode. If you want to use this option, you would have to make sure that you change only tunable parameters. Then you should change these parameters using the "SetVariable" method of the simulation input objects. Then use "setModelParameter" to set the "SimulationMode" to "rapid" and the "RapidAcceleratorUpToDateCheck" to "Off".
If you use a local pool, then you don't need to use "Simulink.BlockDiagram.modifyTunableParameters" or "Simulink.BlockDiagram.buildRapidAcceleratorTarget".
Now, in the above workflow within GO Toolbox, I have named the functions "parsim" and "Simulink.SimulationInput". These are only available since MATLAB R2017a. Here we would really recommend if it is possible to upgrade your release, as "parsim" does a lot of the parallel setup for you, so it might be much harder to get this to work in MATLAB R2016b. Upgrading would probably be the easiest solution here. 

More Answers (0)

Categories

Find more on Manual Performance Optimization in Help Center and File Exchange

Tags

No tags entered yet.

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!