目录
本文详细介绍了MATLAB中的fmincon函数,该函数专门用于寻找带有约束条件的非线性多变量函数的最小值。文章从fmincon的基本语法入手,逐步深入到其应用实例,包括线性不等式约束、线性等式与不等式混合约束、具有边界约束的优化问题、非线性约束优化以及如何获取目标函数值和使用额外输出来验证解的正确性。此外,还探讨了如何获取fmincon的所有输出以及exitflag参数如何帮助理解算法停止的原因。通过综合运用这些方法和技巧,本文旨在帮助读者掌握使用fmincon解决实际优化问题的能力,从而在科研或工程项目中实现高效准确的优化计算。
目录
一、fmincon语法
二、说明
三、示例
(一)线性不等式约束
(二) 线性不等式和等式约束
(三)具有边界约束的最小化
(四) 非线性约束
(五)获得目标函数值
(六)使用额外输出检查解
(七) 获取所有输出
(八) exitflag — fmincon 停止的原因
四、综上
一、fmincon语法
x = fmincon(fun,x0,A,b)x = fmincon(fun,x0,A,b,Aeq,beq)x = fmincon(fun,x0,A,b,Aeq,beq,lb,ub)x = fmincon(fun,x0,A,b,Aeq,beq,lb,ub,nonlcon)x = fmincon(fun,x0,A,b,Aeq,beq,lb,ub,nonlcon,options)x = fmincon(problem)[x,fval] = fmincon(___)[x,fval,exitflag,output] = fmincon(___)[x,fval,exitflag,output,lambda,grad,hessian] = fmincon(___)
二、说明
x = fmincon(fun,x0,A,b)
从 x0
开始,尝试在满足线性不等式 A*x ≤ b
的情况下寻找 fun
中所述的函数的最小值点 x
。x0
可以是标量、向量或矩阵。
x = fmincon(fun,x0,A,b,Aeq,beq)
在满足线性等式 Aeq*x = beq
以及不等式 A*x ≤ b
的情况下最小化 fun
。如果不存在不等式,则设置 A = []
和 b = []
。
x = fmincon(fun,x0,A,b,Aeq,beq,lb,ub)
对 x
中的设计变量定义一组下界和上界,使解始终在 lb
≤ x
≤ ub
范围内。如果不存在等式,请设置 Aeq = []
和 beq = []
。如果 x(i)
无下界,请设置 lb(i) = -Inf
,如果 x(i)
无上界,请设置 ub(i) = Inf
。
x = fmincon(fun,x0,A,b,Aeq,beq,lb,ub,nonlcon)
执行最小化时,满足 nonlcon
所定义的非线性不等式 c(x)
或等式 ceq(x)
。fmincon
进行优化,以满足 c(x) ≤ 0
和 ceq(x) = 0
。如果不存在边界,请设置 lb = []
和/或 ub = []
。
x = fmincon(fun,x0,A,b,Aeq,beq,lb,ub,nonlcon,options)
使用 options
所指定的优化选项执行最小化。使用 optimoptions 可设置这些选项。如果没有非线性不等式或等式约束,请设置 nonlcon = []
。
x = fmincon(problem)
求 problem
的最小值,它是 problem 中所述的一个结构体。
[x,fval] = fmincon(___)
对上述任何语法,返回目标函数 fun
在解 x
处的值。
[x,fval,exitflag,output] = fmincon(___)
还返回描述 fmincon
的退出条件的值 exitflag
,以及提供优化过程信息的结构体 output
。
[x,fval,exitflag,output,lambda,grad,hessian] = fmincon(___)
还返回:
lambda
- 结构体,其字段包含解 x
处的拉格朗日乘数。
grad
- fun
在解 x
处的梯度。
hessian
- fun
在解 x
处的黑塞矩阵。请参阅fmincon Hessian 矩阵。
三、示例
(一)线性不等式约束
在具有线性不等式约束的情况下求 Rosenbrock 函数的最小值。
将目标函数 fun
设置为 Rosenbrock 函数。众所周知,Rosenbrock 函数很难实现最小化。它在点 (1,1) 处的最小目标值为 0。有关详细信息,请参阅使用优化实时编辑器任务或求解器的有约束非线性问题。
从点 [-1,2]
开始求最小值,约束为 x(1)+2x(2)≤1。以 A = [1,2]
和 b = 1
为条件,以 Ax <= b
形式表达此约束。请注意,此约束意味着解不会在无约束解 (1,1) 处,因为在此点处 x(1)+2x(2)=3>1。
fun = @(x)100*(x(2)-x(1)^2)^2 + (1-x(1))^2;
x0 = [-1,2];A = [1,2];b = 1;x = fmincon(fun,x0,A,b)
(二) 线性不等式和等式约束
在既有线性不等式约束又有线性等式约束的情况下求 Rosenbrock 函数的最小值。
将目标函数 fun
设置为 Rosenbrock 函数。
从点 [0.5,0]
开始求最小值,约束为 x(1)+2x(2)≤1 和 2x(1)+x(2)=1。
以 A = [1,2]
和 b = 1
为条件,以 A*x <= b
形式表达线性不等式约束。
以 Aeq = [2,1]
和 beq = 1
为条件,以 Aeq*x = beq
形式表达线性等式约束。
fun = @(x)100*(x(2)-x(1)^2)^2 + (1-x(1))^2;
x0 = [0.5,0];A = [1,2];b = 1;Aeq = [2,1];beq = 1;x = fmincon(fun,x0,A,b,Aeq,beq)
(三)具有边界约束的最小化
在存在边界约束的情况下,求目标函数的最小值。
目标函数是具有两个变量的简单代数函数。
fun = @(x)1+x(1)/(1+x(2)) - 3*x(1)*x(2) + x(2)*(1+x(1));
关注 x 为正值且满足 x(1)≤1 和 x(2)≤2 的区域。
lb = [0,0];ub = [1,2];
该问题没有线性约束,因此将这些参数设置为 []
。
A = [];b = [];Aeq = [];beq = [];
尝试使用一个位于区域中部的初始点。
x0 = (lb + ub)/2;
求解。
x = fmincon(fun,x0,A,b,Aeq,beq,lb,ub)
使用另一个初始点会得到不同的解。
x0 = x0/5;x = fmincon(fun,x0,A,b,Aeq,beq,lb,ub)
(四) 非线性约束
在非线性约束下求函数的最小值
在边界约束下求 Rosenbrock 函数在圆内最小的点。
fun = @(x)100*(x(2)-x(1)^2)^2 + (1-x(1))^2;
在区域
内寻找。
lb = [0,0.2];ub = [0.5,0.8];
同时在以 [1/3,1/3] 为圆心、半径为 1/3 的圆内寻找。将以下代码复制到您的 MATLAB® 路径上名为 circlecon.m
的文件中。
% Copyright 2015 The MathWorks, Inc.function [c,ceq] = circlecon(x)c = (x(1)-1/3)^2 + (x(2)-1/3)^2 - (1/3)^2;ceq = [];
这段代码是用 MATLAB 编写的,它定义了一个名为 `circlecon` 的函数。
这个函数的作用是计算一个点 ( x )(一个二维向量,包含两个元素 ( x_1 ) 和 ( x_2 ))到圆心在 ((1/3, 1/3) )且半径为 1/3 的圆的位置关系。
函数有两个输出参数:
- `c` 是不等式约束条件的结果,它表示了点 ( x ) 到圆心的距离的平方与圆的半径的平方之差。如果 ( c < 0 ),则点 ( x ) 在圆内;如果 ( c = 0 ),则点 ( x ) 在圆上;如果 ( c > 0 ),则点 ( x ) 在圆外。
- `ceq` 是等式约束条件的结果,在这里它是一个空数组 `[]`,表明没有等式约束条件。
没有线性约束,因此将这些参数设置为 []
。
A = [];b = [];Aeq = [];beq = [];
选择一个满足所有约束的初始点。
x0 = [1/4,1/4];
求解。
nonlcon = @circlecon;x = fmincon(fun,x0,A,b,Aeq,beq,lb,ub,nonlcon)
(五)获得目标函数值
带 fval
输出调用 fmincon
,以获得解处的目标函数值。
具有边界约束的最小化示例给出了两个解。哪个更好?运行以下示例,它请求 fval
输出和解。
fun = @(x)1+x(1)./(1+x(2)) - 3*x(1).*x(2) + x(2).*(1+x(1));lb = [0,0];ub = [1,2];A = [];b = [];Aeq = [];beq = [];x0 = (lb + ub)/2;[x,fval] = fmincon(fun,x0,A,b,Aeq,beq,lb,ub)
使用另一个起点 x0
运行问题。
x0 = x0/5;[x2,fval2] = fmincon(fun,x0,A,b,Aeq,beq,lb,ub)
(六)使用额外输出检查解
要轻松检查解的质量,可请求 exitflag
和 output
输出。
设立一个在单位圆盘
上最小化 Rosenbrock 函数的问题。首先创建一个表示非线性约束的函数。将此函数保存为 MATLAB® 路径上名为 unitdisk.m
的文件。
function [c,ceq] = unitdisk(x)c = x(1)^2 + x(2)^2 - 1;ceq = [];
创建其余的问题设定。
fun = @(x)100*(x(2)-x(1)^2)^2 + (1-x(1))^2;nonlcon = @unitdisk;A = [];b = [];Aeq = [];beq = [];lb = [];ub = [];x0 = [0,0];
使用 fval
、exitflag
和 output
输出调用 fmincon
。
[x,fval,exitflag,output] = fmincon(fun,x0,A,b,Aeq,beq,lb,ub,nonlcon)
(七) 获取所有输出
fmincon
可以返回几个输出,您可以使用这些输出来分析报告的解。
设立一个在单位圆盘上最小化 Rosenbrock 函数的问题。首先创建一个表示非线性约束的函数。将此函数保存为 MATLAB® 路径上名为 unitdisk.m
的文件。
function [c,ceq] = unitdisk(x)c = x(1)^2 + x(2)^2 - 1;ceq = [];
创建其余的问题设定。
fun = @(x)100*(x(2)-x(1)^2)^2 + (1-x(1))^2;nonlcon = @unitdisk;A = [];b = [];Aeq = [];beq = [];lb = [];ub = [];x0 = [0,0];
请求所有 fmincon
输出。
[x,fval,exitflag,output,lambda,grad,hessian] = fmincon(fun,x0,A,b,Aeq,beq,lb,ub,nonlcon)
(八) exitflag
— fmincon
停止的原因
fmincon
停止的原因,以整数形式返回。
四、综上
% 定义目标函数 fun1.mfunction f = fun1(x)f = sum(x.^2) + 8;end% 定义非线性约束条件 fun2.mfunction [g, h] = fun2(x)g = [-x(1)^2 + x(2) - x(3)^2, x(1) + x(2)^2 + x(3)^2 - 20];h = [x(2) + 2*x(3)^2 - 3, -x(1) - x(2)^2 + 2];end% 调用 fmincon 函数求解x0 = [1, 1, 1]; % 初始值lb = [0, 0, 0]; % 下界ub = [inf, inf, inf]; % 上界[x, fval] = fmincon('fun1', x0, [], [], [], [], lb, ub, 'fun2');