matlab实现进退法、0.618法、牛顿法

21 篇文章 0 订阅
5 篇文章 2 订阅

实验一 一维最优化方法

实验目的及要求:

  1. 编写程序实现进退法,利用进退法求解极值区间实例;

  2. 编写程序实现0.618 法,利用0.618 法求解极值实例;

  3. 编写程序实现牛顿法,来求解一维函数的局部极小值点。

实验原理:

M a t l a b Matlab Matlab 环境下,按照要求编写函数和程序,求解实例,直至取得正确的运行结果。(写出每种算法的步骤)

算法1:进退法
  1. 设定初始值 α = 2 , k = 0 , ϕ 0 = ϕ ( λ 0 ) \alpha=2,k=0,\phi _0=\phi (\lambda _0) α=2k=0ϕ0=ϕ(λ0),传入参数 h 0 h_0 h0
  2. 使 λ k + 1 = λ k + h k \lambda _{k+1}=\lambda _k+h_k λk+1=λk+hk,计算 ϕ k + 1 = ϕ ( λ k + 1 ) \phi _{k+1}=\phi (\lambda _{k+1}) ϕk+1=ϕ(λk+1)
  3. ϕ k + 1 < ϕ k \phi _{k+1}<\phi _k ϕk+1<ϕk,转向4;反之转向5。
  4. 加步, h k + 1 = a h k , λ = λ k , λ k = λ k + 1 , ϕ k = ϕ k + 1 , k + + h_{k+1}=ah_k,\lambda =\lambda _k,\lambda _k=\lambda _{k+1},\phi _{k}=\phi _{k+1},k{++} hk+1=ahkλ=λkλk=λk+1ϕk=ϕk+1k++,转向2。
  5. 反向探索:
    • k = 0 k=0 k=0则转换方向: h k = − h k , λ = λ k + 1 h_k=-h_k,\lambda =\lambda _{k+1} hk=hkλ=λk+1,转向2。
    • 否则停止迭代, a = m i n ( λ , λ k + 1 ) , b = m a x ( λ , λ k + 1 ) a=min(\lambda ,\lambda _{k+1}),b=max (\lambda ,\lambda _{k+1}) a=min(λ,λk+1)b=max(λ,λk+1),输出 [ a , b ] [a,b] [a,b]
算法2:0.618法
  1. 选取初始区间 [ a 1 , b 1 ] [a_1,b_1] [a1,b1]和误差 ε > 0 \varepsilon>0 ε>0 τ \tau τ=0.618。
  2. 计算 λ 1 = a 1 + ( 1 − τ ) ( b 1 − a 1 ) , μ 1 = a 1 + τ ( b 1 − a 1 ) \lambda_{1}=a_{1}+(1-\tau)\left(b_{1}-a_{1}\right), \mu_{1}=a_{1}+\tau\left(b_{1}-a_{1}\right) λ1=a1+(1τ)(b1a1),μ1=a1+τ(b1a1),并求出 ϕ ( λ 1 ) , ϕ ( μ 1 ) \phi(\lambda_1),\phi(\mu_1) ϕ(λ1)ϕ(μ1) k = 1 k=1 k=1
  3. ∣ b k − a k ∣ < ε \left|b_{k}-a_{k}\right|<\varepsilon bkak<ε,停止计算,输出 t ˉ = λ k + μ k 2 \bar{t}=\frac{\lambda_{k}+\mu_{k}}{2} tˉ=2λk+μk;反之转向4。
  4. 比较函数值
    • ϕ ( λ k ) < ϕ ( μ k ) \phi(\lambda_k)<\phi(\mu_k) ϕ(λk)<ϕ(μk),转向5。
    • 反之,转向6。
  5. 向左搜索,令 a k + 1 = a k , b k + 1 = μ k , μ k + 1 = λ k , φ ( μ k + 1 ) = φ ( λ k ) a_{k+1}=a_{k}, b_{k+1}=\mu_{k}, \mu_{k+1}=\lambda_{k}, \varphi\left(\mu_{k+1}\right)=\varphi\left(\lambda_{k}\right) ak+1=ak,bk+1=μk,μk+1=λk,φ(μk+1)=φ(λk),并计算 λ k + 1 = a k + 1 + ( 1 − τ ) ( b k + 1 − a k + 1 ) \lambda_{k+1}=a_{k+1}+(1-\tau)\left(b_{k+1}-a_{k+1}\right) λk+1=ak+1+(1τ)(bk+1ak+1) φ ( λ k + 1 ) \varphi\left(\lambda_{k+1}\right) φ(λk+1),转向7。
  6. 向右搜索,令 a k + 1 = λ k , b k + 1 = b k , λ k + 1 = μ k , φ ( λ k + 1 ) = φ ( μ k ) a_{k+1}=\lambda_{k}, b_{k+1}=b_{k}, \lambda_{k+1}=\mu_{k}, \varphi\left(\lambda_{k+1}\right)=\varphi\left(\mu_{k}\right) ak+1=λk,bk+1=bk,λk+1=μk,φ(λk+1)=φ(μk),并计算 μ k + 1 = a k + 1 + τ ( b k + 1 − a k + 1 ) \mu_{k+1}=a_{k+1}+\tau\left(b_{k+1}-a_{k+1}\right) μk+1=ak+1+τ(bk+1ak+1) φ ( μ k + 1 ) \varphi\left(\mu_{k+1}\right) φ(μk+1),转向7。
  7. k + + k{++} k++,转向3。
算法3:牛顿法
  1. 设定初始点 t 0 t_0 t0,允许误差 ε > 0 \varepsilon>0 ε>0 k = 0 k=0 k=0
  2. ϕ ′ ( t k ) < ε \phi'(t_k)<\varepsilon ϕ(tk)<ε输出 t k t_k tk,停止计算,反之转向3。
  3. 计算 t k + 1 = t k − φ ′ ( t k ) φ ′ ′ ( t k ) , k + + t_{k+1}=t_{k}-\frac{\varphi^{\prime}\left(t_{k}\right)}{\varphi^{\prime \prime}\left(t_{k}\right)},k{++} tk+1=tkφ(tk)φ(tk)k++,转向2。

实验内容(方法和步骤)

例题
题目1 编写程序实现进退法。

利用Matlab 编写函数 [xmin,xmax]=Brackeing(f,x0,h0). 区间[xmin,xmax] 包含函数f的一个局部极值点。

调用上述函数,实现代码在代码实现部分:

function [xmin,xmax]=Brackeing(f,x0,h)
%{
Brackeing 进退法
   f       函数
   x0      初始点
   h0      步长
   
   xmin    左区间
   xmax    右区间
%}
F = matlabFunction(f);  %建立函数句柄
a = 2;                  %加倍系数
k = 1;                  %迭代数
lambda = 0;             %记录答案
flag = false;           %标记

x = zeros(1,10);        %申请自变量空间
f_val = zeros(1,10);    %申请函数值空间
x(1) = x0;              %自变量赋值
f_val(1) = F(x(1));     %函数赋值


while true
%%%%%%%%%%%%% 试探&计算
    x(k+1) = x(k) + h;      
    f_val(k+1) = F(x(k+1));
%%%%%%%%%%%%%
    if f_val(k+1) >= f_val(k) %  比较
        if k == 1       %检查
            h = -h;     %改变方向反向前进
            lambda = x(k+1);
            x(k+1) = x(k) + h;      
            f_val(k+1) = F(x(k+1));
        else 
            flag = true;
        end
    end
    
    if flag         %结束计算
        break
    end
        
%%%%%%%%%%%%% 加步
    h = a * h;
    lambda = x(k);
    x(k) = x(k+1);
    f_val(k) = f_val(k+1);
    k = k + 1;
%%%%%%%%%%%%%
end

xmin = min(lambda, x(k+1));     %左边界
xmax = max(lambda, x(k+1));     %右边界
disp(xmin)
disp(xmax)
%%%%%%%%%%%%% 绘图查看
figure('Name', 'Brackeing')
xx = xmin-0.5:0.01:xmax+0.5;
yy = F(xx);
plot(xx, yy, 'LineWidth', 2)
hold on
plot([xmin,xmax], [min(yy), min(yy)],':r', 'LineWidth', 1.5)
end
题目2 利用进退法求解极值区间实例

利用进退法求解极值区间实例。取初始点x0=0,步长h0=0.1 ,用进退法求函数 f ( x ) = ( x 2 − 1 ) 2 − ( x − 1 ) 2 f(x)=(x^2-1)^2-(x-1)^2 f(x)=(x21)2(x1)2+3的极值区间。

代码实现部分为:

syms x y;
y = (x^2 - 1)^2 - (x - 1)^2 + 3;
[xmin,xmax]=Brackeing(y,0,0.1);

输出结果为:

xmin = -3.1000
xmax = -0.7000

检查结果为:

在这里插入图片描述

题目3 编写程序实现0.618 法

利用Matlab 编写函数 . 调用函数得到的x 为函数f 在区间[a,b] 上的局部极小值点。

代码实现部分为:

function [x,miny]=MinHJ(f,a,b,eps)
%{
    MinHJ   0.618法
    f       函数
    a       左区间
    b       右区间
    eps     精度

    x       自变量
    miny    局部极小值
%}
xmax = b;
xmin = a;
F = matlabFunction(f);  %函数句柄
tau = 0.618;            %缩短率
lambda = a + (1 - tau)*(b - a);     %计算lambda
mu = a + tau * (b - a);             %计算mu

lambda_val = F(lambda);             %lambda函数值
mu_val = F(mu);                     %mu函数值

while b - a >= eps                  %误差区间之外
    %fprintf('a=%d,b=%d,a_val=%d,b_val=%d\n',a,b,lambda_val,mu_val);
    if lambda_val < mu_val
        b = mu;
        mu = lambda;
        mu_val = lambda_val;
        lambda = a + (1 - tau)*(b - a);
        lambda_val = F(lambda);
    else
        a = lambda;
        lambda = mu;
        lambda_val = mu_val;
        mu = a + tau * (b - a);
        mu_val = F(mu);
    end
end

%计算结果
x = (lambda + mu) / 2;
miny = F(x);

%%%%%%%% 绘图
figure('Name', 'MinHJ')
xx = xmin:0.01:xmax;
yy = F(xx);
plot(xx, yy, 'LineWidth', 2)
hold on
plot(x,miny,'p', 'LineWidth', 2)
end
题目4 利用0.618 法求解极值实例

利用0.618 法求下面函数的极小值: f ( x ) = ( x 2 − 1 ) 2 − ( x − 1 ) 2 + 3 , t ∈ ( − 10 , 10 ) f(x)=\left(x^{2}-1\right)^{2}-(x-1)^{2}+3, t \in(-10,10) f(x)=(x21)2(x1)2+3,t(10,10),误差为0.01

调用上述代码,实现部分为:

syms x y;
y = (x^2 - 1)^2 - (x - 1)^2 + 3;
[x,miny]=MinHJ(y,-10,10,0.01);

在这里插入图片描述

输出结果为:

x = -1.3656
miny = -1.8481

检查结果为:

题目5 编写程序实现牛顿法

利用Matlab 编写函数 [x,minf]=Newton(f,x0,eps). 其中f 为目标函数, x0 为初始点,eps 为算法终止的精度。用牛顿法求解无约束优化问题minf(x) 。

代码实现部分为:

function [x,minf]=Newton(f,x0,eps)
%{
Newton      牛顿法
    f       函数
    x0      初始点
    eps     误差
   
    x       目标x
    minf    目标函数值
%}
xmax = x0+2;
xmin = x0-2;
F0 = matlabFunction(f);             %原函数函数句柄
F1 = matlabFunction(diff(f));       %一阶导函数函数句柄
F2 = matlabFunction(diff(f,2));     %二阶导函数函数句柄

while abs(F1(x0)) >= eps            %迭代
    x0 = x0 - F1(x0) / F2(x0);
end

x = x0;
minf = F0(x);

%%%%%%%% 绘图
figure('Name', 'MinHJ')
xx = xmin:0.01:xmax;
yy = F0(xx);
plot(xx, yy, 'LineWidth', 2)
hold on
plot(x,minf,'p', 'LineWidth', 2)
end


while abs(F1(x0)) >= eps            %迭代
    x0 = x0 - F1(x0) / F2(x0);
end

x = x0;
minf = F0(x);

%%%%%%%% 绘图
figure('Name', 'MinHJ')
xx = xmin:0.01:xmax;
yy = F0(xx);
plot(xx, yy, 'LineWidth', 2)
hold on
plot(x,minf,'p', 'LineWidth', 2)
end
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

数学小牛马

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值