一维搜索:0.618法

0.618法又叫黄金分割法,适用于单峰函数,可以不连续。

1.算法步骤
  • (1) 置初始区间 [ a 1 , b 1 ] 及精度要求 L > 0 ,计算试探点 λ 1 μ 1 ,计算函数值 f ( λ 1 ) f ( μ 1 ) 。计算公式为
    λ 1 = a 1 + 0.382 ( b 1 a 1 ) , μ 1 = a 1 + 0.618 ( b 1 a 1 )
  • (2) 若 b k a k < L ,则停止计算。否则,当 f ( λ k ) > f ( μ k ) 时,转步骤(3);当 f ( λ k ) f ( μ k ) 时,转步骤(4)。
  • (3) 置 a k + 1 = λ k , b k + 1 = b k , λ k + 1 = μ k , μ k + 1 = a k + 1 + 0.618 ( b k + 1 a k + 1 ) 计算函数值 f ( μ k + 1 ) 转步骤(5)。
  • (4) 置 a k + 1 = a k , b k + 1 = μ k , μ k + 1 = λ k , λ k + 1 = a k + 1 + 0.382 ( b k + 1 a k + 1 ) 计算函数值 f ( λ k + 1 ) 转步骤(5)。
  • (5) 置 k := k + 1 ,返回步骤(2)。

2.代码示例
1.测试函数:

clc,clear
func = @(x) 2*x.^2 - x - 1; % 创建函数句柄
a1 = -1;
b1 = 1;
L = 0.01;
tic
[x state] = goldenRatio(func,a1,b1,L); %求解最小值
toc
% 画图展示
x = a1:0.01:b1;
y = 2*x.^2 - x - 1;
axis([-2 2 -10 10])
for k = 1:size(state,1)
figure(1)
plot(x,y,'b'); hold on 
plot(state(k,[1 2]),func(state(k,[1 2])),'ro'); hold off
axis([-2 2 -4 4])
pause(0.4);
end


2.算法函数:

% goldenRatio 黄金分割法
%   - 优点:不要求函数可微,且每次迭代只需计算一个函数值,计算量小,程序简单
%   - 缺点:收敛速度慢
% Inputs:
%   - func  要计算的函数的函数句柄
%   - L > 0 精度
%   - a1    搜索区间下限
%   - b1    搜索区间上限
% Outputs:
%   - res     返回func(x)的最小值
%   - state   返回每次迭代的[a_k b_k lambda_k mu_k f1 f2] 

function [res,state] = goldenRatio(func,a1,b1,L)
%初始化
a_k = a1; 
b_k = b1;
lambda_k = a1 + 0.382*(b1 - a1);
mu_k = a1 + 0.618*(b1 - a1);
f1 = func(lambda_k);
f2 = func(mu_k);

count = 1;
while(true)
    %实际使用时可以去掉state和count,因为会影响运行速度
    state(count,:) = [a_k b_k lambda_k mu_k f1 f2]; 
    count = count + 1;

    if(b_k - a_k < L) break;end
    if(f1 > f2)
        a_k = lambda_k;
        %b_k = b_k; 
        lambda_k = mu_k;
        mu_k = a_k + 0.618*(b_k - a_k);
        f1 = f2;
        f2 = func(mu_k);
    else
        %a_k = a_k;
        b_k = mu_k;
        mu_k = lambda_k;
        lambda_k = a_k + 0.382*(b_k - a_k);
        f2 = f1;
        f1 = func(lambda_k);
    end
end
res = 0.5*(a_k + b_k);
end

3.搜索过程动图:
这里写图片描述
参考书目:《最优化理论与算法》陈宝林

猜你喜欢

转载自blog.csdn.net/sixabs/article/details/81429552