1

次のコードは機能しませんが、これは私が取得しようとしているアイデアです。

        c = @(x)constraints;
        %this is where I would initialize sum as 0 but not sure how...
        for i = 1:length(c)
            sum = @(x)(sum(x) + (min(c(x)(i),0))^2);
        end
        penFunc = @(x)(funcHandle(x) + sig*sum(x));

ここで、constraint と funcHandle は x の関数です。このコード全体は、一連の sig に対して繰り返されます。

明らかに c(x)(i) は機能しません。i での c(x) の最小値 (c(x) はベクトル) または 0 を取得して二乗する関数を作成しようとしています。

c(x) を計算して各 i で分析できることはわかっていますが、最終的には、penFunc の最小値を計算する別の関数のハンドルとして penFunc を渡したいので、それを関数として保持する必要があります。

4

1 に答える 1

2

あなたが達成しようとしていることを完全には理解していないことを認めますが、sum事前計算した変化する値を持つ無名関数の関数ハンドルを作成しようとしているようです。MATLAB の無名関数を使用すると、これを行うことができます。

ここでは、無名関数との混乱があるようです。まず、次の行:

c = @(x)constraints;

c本当に関数ハンドルになりたい場合を除き、おそらく何か別のものであるはずです。行頭の@は、既存の関数を呼び出したいだけだと思う​​ときに、新しい無名関数を宣言しますconstraints。あなたは本当にc制約関数から来る制約の配列になりたいようです。その場合、私はあなたが言うつもりだと思います

c = constraints(x);

次に、和を求めますが、ベクトルとして求めるか、単一の和として求めるかはわかりません。まず、'sum' という名前は付けないようにしましょう。これは組み込みの MATLAB 関数の名前だからです。それを「サムバル」と呼びましょう。値が 1 つだけの場合は簡単です (どちらの方法も簡単ですが、これを実行してみましょう) for ループの前に開始しsumval=0;て初期化すると、ループは次のようになります。

sumval = 0;    
for i = 1:length(c)
    sumval = sumval + (min(c(i),0))^2);
end

必要に応じて、4 行すべてをベクトル化できます。

c(c>0) = 0; %Replace all positive values with 0
sumval = sum(c.^2);  % Use .^ to do a element by element square.

最後の行は明らかに実際の関数ハンドルを作成する場所ですが、ここで何が必要かはまだよくわかりません。が関数の場合sigは、おそらく次のようにするつもりでした:

penFunc = @(x)(funcHandle(x) + sig*sumval);

確信はないけど。sum をベクトルにしたい場合は、ここで指定した方法ではうまくいきません。

実際には、penFunc をその中に変数を持つ無名関数 (つまり、sumval) にすることは問題ありませんが、関数ハンドル宣言の時点で存在していた sumval の値を引き続き使用することに注意してください。

したがって、実際の問題は、A) c の作成です。これは、関数ハンドルを意図したものではないと思います。B) sum の初期化です。これは、おそらく sumval にする必要があります (MATLAB 自体の関数と対話しないため)。おそらく新しい関数ハンドルを宣言すべきではありません。

于 2015-04-14T01:33:04.510 に答える