主要内容

このページの翻訳は最新ではありません。ここをクリックして,英語の最新版を参照してください。

优化工具箱™のチュートリアル

このチュートリアルには,2つの非線形最適化ソルバー(fminuncfmincon)の使用方法とオプションの設定方法を示す複数の例が含まれています。このチュートリアルで紹介する原理は,fgoalattainfminimaxlsqnonlinlsqcurvefitfsolveなどの他の非線形ソルバーにも適用されます。

チュートリアルの例では以下のタスクを取り上げます。

  • 目的関数の最小化

  • 追加のパラメーターを使用した同じ関数の最小化

  • 制約付きの目的関数の最小化

  • 勾配またはヘッシアンを提供するか,オプションを変更することによる,より効率的または正確な解の取得

制約なしの最適化の例

次の関数の最小値を求める問題を考えます。

x 经验值 - x 2 + y 2 + x 2 + y 2 / 2 0

関数をプロットしてそれが最小になる位置を確認します。

F = @(x,y) x.*exp(-x.²-y.²)+(x.²+y.²)/20;fsurf (f (2, 2),“ShowContours”“上”

プロットは,最小値が点(1/2,0)の近くにあることを示しています。

通常は,目的関数をMATLAB®ファイルとして定義します。この場合は,関数が単純なため無名関数として定義します。

Fun = @(x) f(x(1),x(2));

解を求める初期点を設定します。

x0 =[闲置;0);

fminuncの既定の“拟牛顿”アルゴリズムを使用するように最適化オプションを設定します。このステップにより,チュートリアルがすべてのMATLABバージョンで必ず同じように動作するようになります。

选择= optimoptions (“fminunc”“算法”“拟牛顿”);

ソルバーが計算を実行した反復回数を表示します。

选项。显示=“通路”

制約なしの非線形最小化関数fminuncを呼び出します。

[x, fval, exitflag, output] = fminunc(fun,x0,options);
一阶迭代函数-count f(x)步长最优03 -0.3769 0.339 1 6 -0.379694 1 0.286 2 9 -0.405023 1 0.0284 3 12 -0.405233 1 0.00386 4 15 -0.405237 1 3.17e-05 5 18 -0.405237 1 3.35e-08局部最小找到。优化完成是因为梯度的大小小于最优容忍度的值。

ソルバーによって求められた解を表示します。

uncx = x
uncx =2×1-0.6691 - 0.0000

この解での関数値を表示します。

uncf = fval
uncf = -0.4052

この例では,関数評価の回数を効率の尺度として使用します。関数評価の合計回数を表示します。

output.funcCount
ans = 18

追加のパラメーターを使用した制約なしの最適化の例

ここでは,まず,MATLABファイルを使用して,次に,入れ子関数を使用して,特別なパラメーターを追加引数として目的関数に渡します。

前の例で示した目的関数を考えます。

f x y x 经验值 - x 2 + y 2 + x 2 + y 2 / 2 0

次のように(a, b, c)を使用して関数をパラメーター化します。

f x y 一个 b c x - 一个 经验值 - x - 一个 2 + y - b 2 + x - 一个 2 + y - b 2 / c

この関数は,元の目的関数をシフトおよびスケーリングしたバージョンです。

MATLABファイル関数

次のように定義されたbowlpeakfunという名前のMATLABファイル目的関数を考えます。

类型bowlpeakfun
bowlpeakfun TUTDEMO中传递参数的目标函数。% 2008年版权MathWorks公司y = (x(1)——)。* exp (- ((x(1)——)^ 2 + (x (2) - b) ^ 2)) + ((x(1)——)^ 2 + (x (2) - b) ^ 2) / c;

パラメーターを定義します。

= 2;b = 3;c = 10;

MATLABファイルに対する無名関数ハンドルを作成します。

f = @ (x) bowlpeakfun (x, a, b, c)
f =function_handle与价值:@ (x) bowlpeakfun (x, a, b, c)

fminuncを呼び出して,最小値を見つけます。

x0 =[闲置;0);选择= optimoptions (“fminunc”“算法”“拟牛顿”);[x, fval] = fminunc(f,x0,options)
局部最小值。优化完成是因为梯度的大小小于最优容忍度的值。
x =2×11.3639 - 3.0000
fval = -0.3840

入れ子関数

目的を入れ子関数として実装する関数nestedbowlpeakを考えます。

类型nestedbowlpeak
function [x,fval] = nestedbowlpeak(a,b,c,x0,options) % nestedbowlpeak TUTDEMO中的参数传递嵌套函数。%版权2008 MathWorks, Inc. [x,fval] = fminunc(@nestedfun,x0,options);函数y = nestedfun (x) y = (x(1)——)。* exp (- ((x(1)——)^ 2 + (x (2) - b) ^ 2)) + ((x(1)——)^ 2 + (x (2) - b) ^ 2) / c;结束结束

パラメーター(a, b, c)は入れ子目的関数nestedfunに認識されます。外側の関数nestedbowlpeakfminuncを呼び出し,目的関数nestedfunを渡します。

パラメーター,初期推定値,およびオプションを定義します。

= 2;b = 3;c = 10;x0 =[闲置;0);选择= optimoptions (“fminunc”“算法”“拟牛顿”);

最適化を実行します。

[x, fval] = nestedbowlpeak (a, b, c, x0,选项)
局部最小值。优化完成是因为梯度的大小小于最优容忍度的值。
x =2×11.3639 - 3.0000
fval = -0.3840

どちらのアプローチでも同じ結果が得られるため,都合の良い方を選択できます。

制約付き最適化の例:不等式

前の問題を制約付きで考えます。

最小化 x 经验值 - x 2 + y 2 + x 2 + y 2 / 2 0

x y / 2 + x + 2 2 + y - 2 2 / 2 2

この制約は,傾いた楕円の内部です。傾いた楕円と一緒にプロットされた目的関数の等高線を表示します。

F = @(x,y) x.*exp(-x.²-y.²)+(x.²+y.²)/20;G = @(x,y) x.*y/2+(x+2) ^2+(y-2) ^2/2-2;f隐式(g)轴([-6 0 -1 7])保持fcontour (f)情节(-.9727 .4685,“罗”);传奇(“约束”“f轮廓”“最低”);持有

このプロットは,楕円内の目的関数の最小値が楕円の右下付近にあることを示しています。プロットされた最小値を計算する前に,その解を推定します。

X0 = [-2 1];

内点法アルゴリズムを使用して,反復ごとに結果を表示するように,最適化オプションを設定します。

选择= optimoptions (“fmincon”“算法”“内点”“显示”“通路”);

ソルバーには,非線形制約関数からの2つの出力が必要です。第1の出力は非線形不等式で,第2の出力は非線形等式です。両方の出力を提供するために,関数交易を使用して制約を記述します。

@(x) deal(g(x(1),x(2)),[]);

非線形制約付きソルバーを呼び出します。問題に線形の等式,不等式,または範囲は含まれていないため,これらの引数として[]を渡します。

[x, fval exitflag,输出]= fmincon (x0有趣, ,[],[],[],[],[],[], gfun选项);
Iter的一阶范数f -count f(x)可行性优化步骤03 2.365241e-01 0.000e+00 1.972e-01 16 1.748504e-01 0.000e+00 1.7342e -01 2.260e-01 2 10 - 1.1570560e -01 0.000e+00 2.608e-01 9.33e -01 3-2.255299e-01 0.000e+00 1.955e-02 1.993e-02 7 26 -2.444225e-01 0.000e+00 4.293e-03 3.821e-02 8 29 -2.446931e-01 0.000e+00 8.100e-04 4.035e-03 9 32 -2.446933e-01 0.000e+00 1.999e-04 8.126e-04 10 35 -2.448531e-01 0.000e+00 4.004e-05 3.289e-04 11 38 -2.448927e-01 0.000e+00 4.036e-07 8.156e-05 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.

ソルバーによって求められた解を表示します。

x
x =1×2-0.9727 - 0.4686

この解での関数値を表示します。

fval
fval = -0.2449

関数評価の合計回数を表示します。

函数宏指令= output.funcCount
函数宏指令= 38

不等式制約は,この解において満たされます。

[c, ceq] = gfun(x)
c = -2.4608 e-06
测查= []

c (x)が0に近いため,この制約は”アクティブ”です。つまり,解に影響を及ぼします。制約なしの解を再現します。

uncx
uncx =2×1-0.6691 - 0.0000

制約なしの目的関数を再現します。

uncf
uncf = -0.4052

制約によってどのくらい解が移動し,目的が増加したかを確認します。

fval-uncf
ans = 0.1603

制約付き最適化の例:勾配を指定する場合

勾配を指定することによって,最適化問題をより効率的かつ正確に解くことができます。前の例と同様に,この例では,不等式制約付き問題を解きます。

最小化 x 经验值 - x 2 + y 2 + x 2 + y 2 / 2 0

x y / 2 + x + 2 2 + y - 2 2 / 2 2

f (x)の勾配をfminconに与えるために,目的関数をMATLABファイルの形式で記述します。

类型onehump
函数[f,gf] = onehump(x) % onehump Helper function for Tutorial for the Optimization Toolbox demo % Copyright 2008-2009 the MathWorks, Inc. r = x(1)^2 + x(2)^2;s = exp (- r);f = x (1) * s + r / 20;If nargout > 1 gf = [(1-2*x(1)^2)*s+x(1)/10;2 * x (1) * (2) * s + x (2) / 10);结束

制約とその勾配は,MATLABファイルtiltellipseに含まれています。

类型tiltellipse
* tiltellipse(x) /2 + (x(1)+2)^2 + (x(2)-2)^2/2 -2;测查= [];If nargout > 2 gc = [x(2)/2+2*(x(1)+2);(1) / 2 + x (2) 2);gceq = [];结束

解を求める初期点を設定します。

x0 = [2;1);

比較のために前の例と同じアルゴリズムを使用するように最適化オプションを設定します。

选择= optimoptions (“fmincon”“算法”“内点”);

目的関数と制約関数で勾配情報を使用するようにオプションを設定します。メモ:これらのオプションは必ずオンにしてください。そうしないと,勾配情報が無視されます。

选择= optimoptions(选项,...“SpecifyObjectiveGradient”,真的,...“SpecifyConstraintGradient”,真正的);

fminconは有限差分を使用して勾配を推定する必要がないため,ソルバーの関数カウントが少なくなるはずです。反復ごとに結果を表示するようにオプションを設定します。

选项。显示=“通路”

ソルバーを呼び出します。

[x, fval exitflag,输出]= fmincon (x0 @onehump ,[],[],[],[],[],[],...@tiltellipse选项);
1. Iter的一阶Norm f -count f(x)可行性优化步骤01 . Iter的一阶Norm f -count f(x)可行性优化步骤01 . Iter的一阶Norm f -count f(x)可行性优化步骤0局部最小值满足约束条件发现,局部最小值满足约束条件。优化完成是因为目标函数在可行方向上是不递减的,到最优公差的值以内,并且约束满足到约束公差的值以内。

前の例でfminconによる勾配の推定が成功したため,この例での反復も同様です。

ソルバーによって求められた解を表示します。

xold = x
xold =2×1-0.9727 - 0.4686

この解での関数値を表示します。

minfval = fval
minfval = -0.2449

関数評価の合計回数を表示します。

Fgradevals = output.funcCount
Fgradevals = 14

この数字を,勾配を使用しない場合の関数評価回数と比較します。

函数宏指令
函数宏指令= 38

制約付き最適化の例:既定の終了許容誤差の変更

この例では,勾配の使用に進んで,同じ制約付き問題を解きます。

最小化 x 经验值 - x 2 + y 2 + x 2 + y 2 / 2 0

x y / 2 + x + 2 2 + y - 2 2 / 2 2

この場合は,既定の終了基準(选项。StepTolerance选项。OptimalityTolerance)をオーバーライドすることによって,より正確な解を求めます。fmincon内点法アルゴリズムの既定値は选项。StepTolerance = 1平台以及选项。OptimalityTolerance = 1 e-6です。

この2つの既定の終了基準をオーバーライドします。

选择= optimoptions(选项,...“StepTolerance”1 e15汽油,...“OptimalityTolerance”1 e-8);

ソルバーを呼び出します。

[x, fval exitflag,输出]= fmincon (x0 @onehump ,[],[],[],[],[],[],...@tiltellipse选项);
1. Iter的一阶Norm f -count f(x)可行性优化步骤01 . Iter的一阶Norm f -count f(x)可行性优化步骤01 . Iter的一阶Norm f -count f(x)可行性优化步骤0-2.448531e-01 0.000e+00 4.0036e -07 8.156e-05 12 15 -2.448931e-01 0.000e+00 8.00e -09 8.230e-07本地求满足约束条件的最小值。优化完成是因为目标函数在可行方向上是不递减的,到最优公差的值以内,并且约束满足到约束公差的值以内。

新しい許容誤差によって生じる差をより正確に把握するために,解の小数点以下の桁数を増やします。

格式

ソルバーによって求められた解を表示します。

x
x =2×1-0.972742227363546 - 0.468569289098342

これらの値と前の例の値を比較します。

xold
xold =2×1-0.972742694488360 - 0.468569966693330

値の違いを確認します。

x - xold
ans =2×110-6×0.467124813385844 - -0.677594988729435

この解での関数値を表示します。

fval
fval = -0.244893137879894

解がどのくらい改善したかを確認します。

fval——minfval
ans = -3.996450220755676 e-07

新しい解の方が小さいため,答えは負になります。

関数評価の合計回数を表示します。

output.funcCount
ans = 15

この数字を,ユーザー指定の勾配と既定の許容誤差を使用して解いた例の関数評価の回数と比較します。

Fgradevals
Fgradevals = 14

制約付き最適化の例:ユーザー指定のヘッシアン

勾配だけでなくヘッシアンも指定すると,ソルバーの精度と効率がさらに向上します。

fmincon内点法アルゴリズムは,ヘッシアン行列を別個の関数(目的関数の一部ではなく)として取得します。ヘッシアン関数H (x,λ)はラグランジュ関数のヘッシアンを評価します。fminconの内点法アルゴリズムのヘッシアンを参照してください。

ソルバーが,値のlambda.ineqnonlinlambda.eqlinを計算します。ヘッシアン関数が,これらの値の使用方法をソルバーに指示します。

この例には不等式制約が1つしか含まれていないため,ヘッシアンは関数hessfordemoで指定されたように定義されます。

类型hessfordemo
the MathWorks, Inc. s = exp(-(x(1)^2+x(2)^2));H = (2 * x (1) * (2 * x (1) ^ 2 - 3) * s + 1/10, 2 * x (2) * (2 * x(1) ^ 2 - 1) *年代;2 * x (2) * (2 * x (1) ^ 2 - 1) * s, 2 * x (1) * (2 * x (2) ^ 2 - 1) * s + 1/10);hessc = (2 1/2; 1/2, 1);H = H + lambda.ineqnonlin(1)*hessc;

このヘッシアンを使用するには,オプションを適切に設定しなければなりません。

选择= optimoptions (“fmincon”...“算法”“内点”...“SpecifyConstraintGradient”,真的,...“SpecifyObjectiveGradient”,真的,...“HessianFcn”, @hessfordemo);

許容誤差は既定値に設定されるため,関数のカウントは減るはずです。反復ごとに結果を表示するようにオプションを設定します。

选项。显示=“通路”

ソルバーを呼び出します。

[x, fval exitflag,输出]= fmincon (x0 @onehump ,[],[],[],[],[],[],...@tiltellipse选项);
Iter的一阶范数f -count f(x)可行性优化步骤01- 2.44687e -01 0.000e+00 2.057e-04 2.727e-03 7 10 -2.448911e-01 0.000e+00 2.057e-04 4.218e-06局部最小值满足约束。优化完成是因为目标函数在可行方向上是不递减的,到最优公差的值以内,并且约束满足到约束公差的值以内。

結果は,反復回数が少なくなり,異なる反復が示されます。

ソルバーによって求められた解を表示します。

x
x =2×1-0.972742246093537 - 0.468569316215571

この解での関数値を表示します。

fval
fval = -0.244893121872758

関数評価の合計回数を表示します。

output.funcCount
ans = 11

この数字を,既定の許容誤差を同じにし,勾配評価のみを使用して解いた例の関数評価の回数と比較します。

Fgradevals
Fgradevals = 14

関連するトピック