surrogateopt решатель принимает и целочисленные ограничения и нелинейные ограничения. Сравните решение нелинейной проблемы и с и без целочисленных ограничений. Целочисленные ограничения вызывают решение лечь на довольно прекрасную сетку.
Целевая функция
Эта целевая функция является неотрицательной, и принимает свое минимальное значение 0 в точке = [1.3333, 1.0370].
Проблема имеет две нелинейных ограничительных функции.
Постройте выполнимую область для нелинейных ограничений.
[X,Y] = meshgrid(-2:.01:3); Z = (5*sinh(Y./5) >= X.^4); % Z=1 where the first constraint is satisfied, Z=0 otherwise Z = Z+ 2*(5*tanh(X./5) >= Y.^2 - 1); % Z=2 where the second constraint is satisfied % Z=3 where both constraints are satisfied surf(X,Y,Z,'LineStyle','none'); fig = gcf; fig.Color = 'w'; % white background view(0,90) xlabel('x_1') ylabel('x_2')

Желтая область показывает, где обоим ограничениям удовлетворяют.
surrogateopt требует, чтобы цель и ограничительные функции были частью той же функции, та, которая возвращает структуру. Целевая функция находится в Fval поле структуры и ограничения находятся в Ineq поле . Этими полями является выход objconstr функция в конце этого примера.
Установите проблему иметь целочисленные ограничения в обеих переменных, x(1) и x(2).
intcon = [1 2];
Масштабируйте проблему так, чтобы переменные масштабировались s = 1/10, где s умножает переменные.
s = 0.1; f = @(x)objconstr(x,s);
Для этого масштабирования, чтобы быть эффективными, необходимо масштабировать границы . Установите немасштабированные границы на и масштабируйте каждого .
lb = [-2,-2]/s; ub = [3,3]/s;
При помощи масштабирующегося s, проблема эффективно имеет интервал s в каждом x(1) компонента и x(2). Постройте целочисленные точки как сетку с разрядкой s.
hold on grid on ax = gca; sp = -2:s:3; ax.XTick = sp; ax.YTick = sp; ax.Layer = 'top'; ax.GridAlpha = 1/2; ax.XTickLabel = ''; ax.YTickLabel = ''; xlabel('x_1') ylabel('x_2') hold off

Установите опции использовать более трудные ограничения, чем значение по умолчанию и использовать surrogateoptplot функция plot.
opts = optimoptions('surrogateopt','PlotFcn',"surrogateoptplot","ConstraintTolerance",1e-6);
Вызовите surrogateopt решать задачу.
rng default % For reproducibility [sol,fval,eflag,outpt] = surrogateopt(f,lb,ub,intcon,opts)

Surrogateopt stopped because it exceeded the function evaluation limit set by 'options.MaxFunctionEvaluations'.
sol = 1×2
5 1
fval = 0.8634
eflag = 0
outpt = struct with fields:
elapsedtime: 38.2519
funccount: 200
constrviolation: -0.0375
ineq: [-0.0375 -1.4883]
rngstate: [1x1 struct]
message: 'Surrogateopt stopped because it exceeded the function evaluation limit set by ...'
Постройте решение как красный круг на фигуре. Заметьте, что значение целевой функции - приблизительно 0,86.
figure(fig); hold on plot3(sol(1)*s,sol(2)*s,5,'ro') hold off

Сравните решение с целочисленными ограничениями к решению без целочисленных ограничений.
[sol2,fval2,eflag2,outpt2] = surrogateopt(f,lb,ub,[],opts)

Surrogateopt stopped because it exceeded the function evaluation limit set by 'options.MaxFunctionEvaluations'.
sol2 = 1×2
4.3991 0.3746
fval2 = 0.8153
eflag2 = 0
outpt2 = struct with fields:
elapsedtime: 31.0049
funccount: 200
constrviolation: -5.2624e-06
ineq: [-5.2624e-06 -1.4374]
rngstate: [1x1 struct]
message: 'Surrogateopt stopped because it exceeded the function evaluation limit set by ...'
Здесь, значение целевой функции - приблизительно 0,815. Целочисленные ограничения увеличивают значение целевой функции меньше чем на 10%. Постройте новое решение наряду с предыдущим целочисленным решением. Увеличьте масштаб, чтобы видеть точки решения более ясно.
figure(fig) hold on plot3(sol2(1)*s,sol2(2)*s,5,'k*','MarkerSize',12) xlim([0 1]) ylim([-1/2 1/2]) hold off

Этот код создает objconstr функция помощника. Эта функция масштабирует переменную x факторным s, возвращает значение целевой функции в Fval поле F структура, и возвращает нелинейные ограничения в Ineq поле F структура.
function F = objconstr(x,s) x = x*s; fun = log(1 + 3*(x(2) - (x(1)^3 - x(1)))^2 + (x(1) - 4/3)^2); c1 = x(1)^4 - 5*sinh(x(2)/5); c2 = x(2)^2 - 5*tanh(x(1)/5) - 1; c = [c1 c2]; F.Fval = fun; F.Ineq = c; end