Проектируйте параметры оптимизации настройки в ссылочных моделях (код)

В этом примере показано, как настроить параметры в ссылочных моделях, используя sdo.optimize команда.

Модель управления двигателем

Модель показывает управление угловым положением для двух двигателей. Откройте модель Simulink.

open_system('sdoMultipleMotors')

Управление осуществляется двумя двигателями. Модели-ссылки используются для контроллеров, которые являются образцами одной модели. Откройте контроллер.

open_system('sdoRateLimitedController')

Задача проекта

Два двигателя в основной модели имеют различные характеристики, поэтому каждый контроллер должен быть адаптирован к своему двигателю. Каждый контроллер имеет коэффициенты ПИД Kp, Ki, и Kd, и скорость нарастания, Slew. The Slew значение ограничивает скорость, с которой изменяется сигнал управления. The Slew значение является общим для обоих образцов контроллера. Напротив, коэффициенты ПИД должен быть различным для каждого образца контроллера, поскольку управляемые двигатели имеют различные характеристики. Поэтому коэффициенты ПИД заданы как аргументы модели в рабочем пространстве модели контроллера. Значения коэффициента ПИД устанавливаются на уровне sdoMultipleMotors модель.

Управляющий опорный сигнал является шагом изменения положения, которое происходит через 1 секунду. Угловое положение каждого мотора должно следовать за опорным сигналом, но первый двигатель имеет меньший момент инерции и может быстрее реагировать на изменения в опорном сигнале. Кроме того, производная от каждого сигнала контроллера должна быть ограничена, так что токи, вытянутые из источника степени, остаются в пределах источника степени.

Задайте конструктивные переменные

Задайте переменные проекты, которые будут настроены стандартной программой оптимизации порядка чтобы удовлетворить требования. The Slew переменная задается как sdoRateLimitedController:Slew, что указывает на то, что переменная установлена на уровне sdoRateLimitedController модель. Двоеточие является разделителем между моделью и переменной. The Slew переменная имеет то же значение для всех образцов моделей контроллеров. В противоположность этому пропорциональная составляющая для первого контроллера задаётся как sdoMultipleMotors/Control_1:Kp, что указывает на то, что переменная установлена на уровне sdoMultipleMotors модель, где она появляется в Control_1 блок. Прямая косая черта является разделителем для блокпутей Simulink.

Задайте, чтобы конструктивные переменные включали коэффициент усиления Kp, Ki, и Kd, для обоих ПИД-регуляторов. Также включите скорость нарастания, Slew, что является общим для обоих контроллеров. Наконец, задайте, что скорость нарастания не может быть отрицательной.

DesignVars = sdo.getParameterFromModel('sdoMultipleMotors', ...
    {'sdoRateLimitedController:Slew', ...
    ...
    'sdoMultipleMotors/Control_1:Kp', ...
    'sdoMultipleMotors/Control_1:Ki', ...
    'sdoMultipleMotors/Control_1:Kd', ...
    ...
    'sdoMultipleMotors/Control_2:Kp', ...
    'sdoMultipleMotors/Control_2:Ki', ...
    'sdoMultipleMotors/Control_2:Kd' });
DesignVars(1).Minimum = 0;

Задайте требования проект

Угол углового положения каждого мотора должен следовать за опорным сигналом, но первый двигатель имеет меньший момент инерции и может быстрее реагировать на изменения в опорном сигнале. Мы хотим, чтобы угловое положение первого мотора удовлетворяло следующим требованиям:

  • Время нарастания: 2 секунд

  • Время урегулирования: 7 секунд

Это требование задано в блоке проверки переходной характеристики в модели Simulink. Мы можем обратиться к блоку и включить требование в переменную, которая будет передана в целевую функцию оптимизации.

Requirements = struct;
bnds = getbounds('sdoMultipleMotors/Motor1_Step_Response');
Requirements.Motor1_StepResponse = bnds{1};

Второй двигатель имеет больший момент инерции, поэтому он не может реагировать так быстро. Мы хотим, чтобы угловое положение второго мотора удовлетворяло следующим требованиям:

  • Время нарастания: 8 секунд

  • Время урегулирования: 10 секунд

Это требование также задано в блоке проверки переходной характеристики в модели Simulink, и мы ссылаемся на блок, чтобы включить требование в переменную, которая будет передана в целевую функцию оптимизации.

bnds = getbounds('sdoMultipleMotors/Motor2_Step_Response');
Requirements.Motor2_StepResponse = bnds{1};

Кроме того, производная каждого сигнала контроллера должна быть в области значений от -5 до 5, так что токи, вытянутые из источника степени, остаются в пределах источника степени. Эти требования заданы в связанных проверочных блоках в модели Simulink, и эти требования также должны быть собраны среди требований, которые должны быть переданы в целевую функцию оптимизации.

bnds = getbounds('sdoMultipleMotors/ReqBounds_Derivative_Controller1');
Requirements.Controller1_DerivBound1 = bnds{1};
Requirements.Controller1_DerivBound2 = bnds{2};
bnds = getbounds('sdoMultipleMotors/ReqBounds_Derivative_Controller2');
Requirements.Controller2_DerivBound1 = bnds{1};
Requirements.Controller2_DerivBound2 = bnds{2};

Предотвратите значения контрольных блоков во время оптимизации.

CheckBlockStatus = sdo.setCheckBlockEnabled('sdoMultipleMotors','off');

Определение симуляции

Функция стоимости требует сценария симуляции, чтобы запустить модель. Создайте сценарий симуляции и добавьте сигналы модели в журнал, чтобы их значения были доступны функции затрат.

Simulator = sdo.SimulationTest('sdoMultipleMotors');

Угловое положение двигателя должно регистрироваться во время оптимизации, чтобы оценить требования к их переходным характеристикам.

Motor1_Position = Simulink.SimulationData.SignalLoggingInfo;
Motor1_Position.BlockPath = 'sdoMultipleMotors/Motor1_Step_Response/u';
Motor1_Position.LoggingInfo.LoggingName = 'Motor1_Position';
Motor1_Position.LoggingInfo.NameMode = 1;

Motor2_Position = Simulink.SimulationData.SignalLoggingInfo;
Motor2_Position.BlockPath = 'sdoMultipleMotors/Motor2_Step_Response/u';
Motor2_Position.LoggingInfo.LoggingName = 'Motor2_Position';
Motor2_Position.LoggingInfo.NameMode = 1;

Производные сигнала контроллера также должны быть записаны, чтобы оценить связанные требования к ним.

Controller1_Derivative = Simulink.SimulationData.SignalLoggingInfo;
Controller1_Derivative.BlockPath = 'sdoMultipleMotors/ReqBounds_Derivative_Controller1/u';
Controller1_Derivative.LoggingInfo.LoggingName = 'Controller1_Derivative';
Controller1_Derivative.LoggingInfo.NameMode = 1;

Controller2_Derivative = Simulink.SimulationData.SignalLoggingInfo;
Controller2_Derivative.BlockPath = 'sdoMultipleMotors/ReqBounds_Derivative_Controller2/u';
Controller2_Derivative.LoggingInfo.LoggingName = 'Controller2_Derivative';
Controller2_Derivative.LoggingInfo.NameMode = 1;

Чтобы записать эти сигналы во время оптимизации, соберите их в сценарий симуляции, Simulator.

Simulator.LoggingInfo.Signals = [...
    Motor1_Position ; ...
    Motor2_Position ; ...
    Controller1_Derivative ; ...
    Controller2_Derivative ];

Создайте целевую функцию оптимизации

Создайте целевую функцию, которая будет вызываться при каждой итерации оптимизации, чтобы оценить требования проекта по мере настройки конструктивных переменных. Эта функция затрат имеет входные параметры для переменных проекта, сценария симуляции и требований проекта.

type sdoMultipleMotors_Design
function Vals = sdoMultipleMotors_Design(P,Simulator,Requirements)
%SDOMULTIPLEMOTORS_DESIGN Objective function for multiple motors
%
% Function called at each iteration of the optimization problem.
%
% The function is called with the model named mdl, a set of parameter
% values, P, a Simulator, and the design Requirements to evaluate.  It
% returns the objective value and constraint violations, Vals, to the
% optimization solver.
%
% See the sdoExampleCostFunction function and sdo.optimize for a more
% detailed description of the function signature.
%
% See also sdoMultipleMotors_cmddemo

% Copyright 2018 The MathWorks, Inc.

%% Model Evaluation

% Simulate the model.
Simulator.Parameters = P;
Simulator = sim(Simulator);

% Retrieve logged signal data.
SimLog = find(Simulator.LoggedData, get_param('sdoMultipleMotors','SignalLoggingName'));
Motor1_Position = find(SimLog,'Motor1_Position');
Motor2_Position = find(SimLog,'Motor2_Position');
Controller1_Derivative = find(SimLog,'Controller1_Derivative');
Controller2_Derivative = find(SimLog,'Controller2_Derivative');

% Evaluate the design requirements.
Cleq_Motor1_StepResponse     = evalRequirement(Requirements.Motor1_StepResponse,     Motor1_Position.Values);
Cleq_Motor2_StepResponse     = evalRequirement(Requirements.Motor2_StepResponse,     Motor2_Position.Values);
Cleq_Controller1_DerivBound1 = evalRequirement(Requirements.Controller1_DerivBound1, Controller1_Derivative.Values);
Cleq_Controller1_DerivBound2 = evalRequirement(Requirements.Controller1_DerivBound2, Controller1_Derivative.Values);
Cleq_Controller2_DerivBound1 = evalRequirement(Requirements.Controller2_DerivBound1, Controller2_Derivative.Values);
Cleq_Controller2_DerivBound2 = evalRequirement(Requirements.Controller2_DerivBound2, Controller2_Derivative.Values);

%% Return Values.
%
% Collect the evaluated design requirement values in a structure to
% return to the optimization solver.
Vals.Cleq = [...
    Cleq_Motor1_StepResponse(:); ...
    Cleq_Motor2_StepResponse(:); ...
    Cleq_Controller1_DerivBound1(:); ...
    Cleq_Controller1_DerivBound2(:); ...
    Cleq_Controller2_DerivBound1(:); ...
    Cleq_Controller2_DerivBound2(:)];

end

Чтобы оптимизировать, задайте указатель на функцию затрат, которая использует Simulator и Requirements определено выше. Используйте анонимную функцию, которая принимает один аргумент (переменные проекта) и вызывает целевую функцию. Наконец, вызовите sdo.optimize, чтобы оптимизировать переменные проекты, чтобы попытаться удовлетворить требования.

optimfcn = @(P) sdoMultipleMotors_Design(P, Simulator, Requirements);
[Optimized_DesignVars, Info] = sdo.optimize(optimfcn, DesignVars);
 Optimization started 27-Jan-2021 14:57:48

                               max                     First-order 
 Iter F-count        f(x)   constraint    Step-size    optimality
    0     15            0        211.8
    1     30            0        8.464         2.92         26.5
    2     50            0        6.531        0.396         15.1
    3     70            0        1.931        0.675         15.7
    4     85            0       0.2419         1.67         41.2
    5    100            0      0.04524        0.271     1.02e+03
    6    110            0      0.04524      0.00399            0
Local minimum found that satisfies the constraints.

Optimization completed because the objective function is non-decreasing in 
feasible directions, to within the value of the optimality tolerance,
and constraints are satisfied to within the value of the constraint tolerance.

Восстановите значения контрольных блоков.

sdo.setCheckBlockEnabled('sdoMultipleMotors', CheckBlockStatus);

Обновление модели

Обновите модель с оптимизированными значениями параметров.

sdo.setValueInModel('sdoMultipleMotors',Optimized_DesignVars);

Закройте модели.

bdclose('sdoMultipleMotors')
bdclose('sdoRateLimitedController')

Похожие темы