差分进化算法总结

版权声明:转载请联系邮箱[email protected] https://blog.csdn.net/weixin_42528077/article/details/82779819

基本介绍

DE(Differential Evolution)算法于1997年由Rainer Storn和Kenneth Price在遗传算法等进化思想的基础上提出的,本质是一种多目标(连续变量)优化算法,用于求解多维空间中整体最优解。其基本思想即是来源于遗传算法,模拟遗传算法中的杂交、变异、复制来设计算子。

DE算法和GA算法的相同点:

  • 随机生成初始种群
  • 以种群中个体适应度值为选择标准
  • 主要过程包括变异、杂交、选择三个步骤

DE算法和GA算法的区别:

  • DE算法的变异向量是由父代差分向量生成,与父代个体向量交叉生成新个体向量
  • 新个体向量与父代个体一起进行选择

基本算法框架

算法框架

种群初始化

在解空间内随机均匀的产生M个个体。每个个体是一个n为向量:

X i ( 0 ) = X i , 1 ( 0 ) + X i , 2 ( 0 ) + . . . + X i , n ( 0 ) , i = 1 , 2 , 3 , . . . , M X_{i}(0) = X_{i,1}(0) + X_{i,2}(0) + ... + X_{i,n}(0), \qquad i = 1,2,3,...,M

其中 X i ( 0 ) X_{i}(0) 表示第0代的第i个个体, X i , j ( 0 ) X_{i,j}(0) 表示第0代第i个个体的第j个基因。注意:每个个体代表解空间内的某一个解,而基因代表解的各个分量(和遗传算法一样,遗传算法的每个个体的染色体二进制码在一起代表了一个解)。

种群初始化的方式如下:(其实就是在范围内随机产生个体)

f o r   i   =   1 : M for\ i\ =\ 1:M
f o r   j   =   1 : n \qquad for\ j\ =\ 1:n
X i , j ( 0 ) = L j m i n + r a n d ( 0 , 1 ) ( L j m a x L j m i n ) \qquad \qquad X_{i,j}(0) = L_j^{min} + rand(0,1)*(L_j^{max} - L_j^{min})
e n d \qquad end
e n d end

变异算子

在第g次迭代中,对于个体 X i ( g ) = ( X i , 1 ( g ) + X i , 2 ( g ) + . . . + X i , n ( g ) ) X_i(g) = (X_{i,1}(g) + X_{i,2}(g) + ... + X_{i,n}(g)) ,如下生成一个一号中间向量 H i ( g ) H_i(g) :从种群中随机选择三个个体 X p 1 ( g ) , X p 2 ( g ) , X p 3 ( g ) X_{p1}(g), X_{p2}(g), X_{p3}(g) ,且 p 1 p 2 p 3 p1 \neq p2 \neq p3 ,则有

H i ( g ) = X p 1 ( g ) + F ( X p 2 ( g ) X p 3 ( g ) ) H_i(g) = X_{p1}(g) + F*(X_{p2}(g) - X_{p3}(g))

其中 Δ p 2 , p 3 ( g ) = X p 2 ( g ) X p 3 ( g ) \Delta_{p2,p3}(g) = X_{p2}(g) - X_{p3}(g) 是差分向量; F F 是缩放引子,用于控制差分向量的影响力。其几何意义如下图所示:

几何意义

交叉算子

引入交叉算子可以增强种群的多样性。在第g次迭代中,对于每个个体和它所生成的一号中间向量进行交叉,具体的说就是对每一个等位基因(分量)按照一定的概率选择一号中间向量(否则就是原向量)来生成二号中间向量 V i ( g ) V_i(g) V i ( g ) V_i(g) 的每一个分量按照如下公式计算:

v i , j ( g ) = { h i , j ( g ) , r a n d ( 0 , 1 ) P c r x i , j ( g ) , e l s e v_{i,j}(g)= \begin{cases} h_{i,j}(g), \quad rand(0,1) \leq P_{cr} \\ x_{i,j}(g), \quad else \end{cases}

其中 P c r P_{cr} 为交叉概率。交叉过程如下图所示:

交叉过程

选择算子

该过程根据适应度函数的值从第g次迭代中每个个体的二号中间向量 V i ( g ) V_i(g) 和原向量 X i ( g ) X_i(g) 中选择出适应度更高的作为下一代。

注意:不是在所有的 V i ( g ) V_i(g) X i ( g ) X_i(g) 的总共 2 M 2M 个个体中选出适应度最高的那 M M 个个体,而是对于这一代的每个个体的 V i ( g ) V_i(g) X i ( g ) X_i(g) 都进行一次判断,留下适应度最好的那个作为下一代同样位置上的个体。

公式表示如下:

X i ( g + 1 ) = { V i ( g ) , i f   f ( V i ( g ) ) > f ( X i ( g ) ) X i ( g ) , e l s e X_{i}(g+1) = \begin{cases} V_i(g), \quad if \ f(V_i(g)) > f(X_i(g)) \\ X_i(g), \quad else \end{cases}

这样的选择算子操作有如下性质:

  • 对于每个个体, X i ( g + 1 ) X_i(g+1) 一定要优于 X i ( g ) X_i(g)
  • 算法最终肯定会收敛到某个最优点(可能是局部最优);
  • 变异、交叉操作有助于跳出局部最优到达全局最优。

MATLAB代码实现

准备使用差分进化算法求解

f ( x , y ) = 20 e 0.2 x 2 + y 2 2 e c o s   2 π x   +   c o s   2 π y 2 + 20 + e f(x,y) = -20 e^{-0.2 \sqrt{\frac{x^2+y^2}{2}}} - e^{\frac{cos \ 2 \pi x \ +\ cos \ 2\pi y}{2}} + 20 + e

这个神一般的函数在区间 [ 4 , 4 ] [-4,4] 上的最小值。该函数的图像如下,根据图像易知最小值点为 ( 0 , 0 ) (0,0) ,最小值为0。

如图所示

MATLAB代码如下:

% 使用差分进化算法计算这个函数f = @(x,y) -20.*exp(-0.2.*sqrt((x.^2+y.^2)./2))-exp((cos(2.*pi.*x)+cos(2.*pi.*y))./2)+20+exp(1) 在区间[-4,4]上的最小值
% 它真正的最小值点是(0,0)

N = 20; %设置种群数量
F = 0.5; %设置差分缩放因子
P_cr = 0.5; %设置交叉概率
T = 300; %设置最大迭代次数
f = @(x,y) -20.*exp(-0.2.*sqrt((x.^2+y.^2)./2))-exp((cos(2.*pi.*x)+cos(2.*pi.*y))./2)+20+exp(1); %定义目标函数

%种群初始化
population = -4 + rand(N,2).*8;
t = 0; %代数初始化
%开始迭代
while t < T
    %变异
    H_pop = [];
    for i = 1:N
        index = round(rand(1,3).*19)+1;
        add_up = population(index(1),:) + F.*(population(index(2),:)-population(index(3),:));
        H_pop = [H_pop; add_up];
    end
    %交叉
    V_pop = H_pop;
    for i = 1:N
        for j = 1:2
            if rand > P_cr
                V_pop(i,j) = population(i,j);
            end
        end
    end
    %选择
    for i = 1:N
        f_old = f(population(i,1),population(i,2));
        f_new = f(V_pop(i,1),V_pop(i,2));
        if f_new < f_old
            population(i,:) = V_pop(i,:);
        end
    end
    %更新t值
    t = t + 1;
end
population

代码输出结果如下:

代码结果

可以看到最后的种群几乎所有个体都趋于最优解(0,0)。
(最后喷一句新版markdown编辑器居然不识别MATLAB代码,不能高亮!!!)

猜你喜欢

转载自blog.csdn.net/weixin_42528077/article/details/82779819