使用fminunc函数

raj*_*pit 3 matlab convex-optimization

我试图使用fminunc函数进行凸优化.但是,在我的情况下,我正在考虑与logx相关的渐变.让我的目标函数为F.然后梯度将是

dF/dx = (dF/dlogx) * (1/x)
= > dF/dlogx = (dF/dx) * x
Run Code Online (Sandbox Code Playgroud)

所以

logx_new = logx_old + learning_rate * x * (dF/logx)
x_new = exp(logx_new)
Run Code Online (Sandbox Code Playgroud)

我怎样才能在fminunc中实现它

Gun*_*uyf 7

这可能并在文档中描述:

如果也可以计算fun的渐变并且GradObj选项为'on',由options = optimset('GradObj','on')设置,则函数fun必须在第二个输出参数中返回渐变值g ,一个向量,在x.

带有自定义渐变的fminunc

例如:如果f = @(x) x.^2;那么df/dx = 2*x你可以使用

function [f df] = f_and_df(x)
    f = x.^2;
    if nargout>1
        df = 2*x;
    end
end
Run Code Online (Sandbox Code Playgroud)

然后,您可以将该函数传递给fminunc:

options = optimset('GradObj','on');
x0 = 5;
[x,fval] = fminunc(@f_and_df,x0,options);
Run Code Online (Sandbox Code Playgroud)

带有logx渐变的fminunc

对于logx渐变,这将变为:

function [f df] = f_and_df(x)
    f = ...;
    if nargout>1
        df =  x * (dF/logx);
    end
end
Run Code Online (Sandbox Code Playgroud)

fminunc保持不变.

fminunc具有匿名功能

如果需要,您还可以使用匿名函数:

f_and_df2 = @(x) deal(x(1).^2+x(2).^2,[2*x(1)  2*x(2)]);
[x,fval] = fminunc(f_and_df2,[5, 4],optimset('GradObj','on'))
Run Code Online (Sandbox Code Playgroud)

带有logx渐变的fminunc示例

附加示例 f = (log(x))^2

function [f df_dlogx] = f_and_df(x)
    f = log(x).^2;

    df_dx = 2*log(x)./x;
    df_dlogx = df_dx.* x;
end
Run Code Online (Sandbox Code Playgroud)

然后:

>>x0=3;
>>[x,fval] = fminunc(@f_and_df,x0,optimset('GradObj','on'))
x =
   0.999999990550151

fval =
   8.92996430424197e-17
Run Code Online (Sandbox Code Playgroud)

带有自定义渐变和多个变量的fminunc示例

对于多个变量,例如f(x,y),您必须将变量放入向量中,例如:

function [f df_dx] = f_and_df(x)
    f = x(1).2 + x(2).^2;

    df_dx(1) = 2*x(1);
    df_dx(2) = 2*x(2);
end
Run Code Online (Sandbox Code Playgroud)

此功能对应于抛物面.当然,您还必须使用向量作为初始启动参数,在这种情况下例如:x0 = [ - 5 3]