粒子群算法的python实现

本文章提供了一个基础的粒子群算法,以求解函数:

                ​​​​​​​        ​​​​​​​        ​​​​​​​        f(x_{1},x_{2},x_{3},x_{4})=x_{1}^2+ x_{2}^2+ x_{3}^2+ x_{4}^2

其中-10\leqslant x_{1},x_{2},x_{3},x_{4}\leqslant 10,以求解该函数的最小值,来解释粒子群算法。

粒子群算法流程:

Step1. 初始化种群规模为N,在搜索空间中随机初始化每个粒子的速度和位置,并且得到粒子的历史最佳位置和种群的全局最佳位置;

Step2. 对种群每个粒子的速度和位置进行更新,更新公式为:

        ​​​​​​​        v_{i}=\omega \cdot v_{i}+c_{1}\cdot r_{1}\cdot(p_{best}-p_{i})+c_{2}\cdot r_{2}\cdot (g_{best}-p_{i})

                p_{i}=p_{i}+v_{i}

Step3. 评估粒子的适应度函数值 更新粒子的历史最优位置和全局最优位置;

Step4. 如果满足终止条件,则输出全局最佳位置并结束程序,否则转向Step2.继续执行。

完整代码如下:

import numpy as np

# 以求一个函数最小值为例,使用粒子群算法进行问题求解
# 目标函数,其中x1,x2,x3,x4的取值范围[-10, 10]


def goal_function(x1, x2, x3, x4):
    return x1**2 + x2**2 + x3**2 + x4**2


class PSO:
    def __init__(self, group_size, space_dim):
        self.group_size = group_size
        self.search_space_dim = space_dim
        self.best_position_globe = np.zeros(self.search_space_dim)
        self.best_position_globe_value = 400
        self.best_position = np.zeros([self.group_size, self.search_space_dim])
        self.eval = np.zeros(self.group_size)

    def initialize(self):
        group_speed = np.random.uniform(-10, 10, [self.group_size, self.search_space_dim])
        group_position = np.random.uniform(-10, 10, [self.group_size, self.search_space_dim])
        print(f"初始化种群,种群规模为:{self.group_size},搜索空间的维度为:{self.search_space_dim}")
        globe_idx = 0
        for i in range(self.group_size):
            self.eval[i] = goal_function(group_position[i][0], group_position[i][1], group_position[i][2], group_position[i][3])
            self.best_position[i] = group_position[i]
            if self.eval[i] < self.best_position_globe_value:
                self.best_position_globe_value = self.eval[i]
                globe_idx = i
            print(f"第{i+1}号个体的")
            print(f"当前位置为:{group_position[i]}\n局部最佳位置为:{self.best_position[i]}\n速度为:{group_speed[i]}\n适应值为:{self.eval[i]}")
        self.best_position_globe = group_position[globe_idx]
        print(f"全局最佳位置为:{self.best_position_globe}, 全局最佳适应值为:{self.best_position_globe_value}")
        return group_speed, group_position

    def update(self, w=0.8, c1=2, c2=2, r1=0.5, r2=0.5):
        print("种群开始更新")
        for i in range(self.group_size):
            self.group_speed[i] = (w*self.group_speed[i]
                                   +c1*r1*(self.best_position[i]-self.group_position[i])
                                   +c2*r2*(self.best_position_globe-self.group_position[i]))
            self.group_position[i] = self.group_position[i] + self.group_speed[i]

    def evaluate(self):
        temp_eval = np.zeros(self.group_size)
        for i in range(self.group_size):
            temp_eval[i] = goal_function(self.group_position[i][0], self.group_position[i][1], self.group_position[i][2], self.group_position[i][3])
            if temp_eval[i] < self.eval[i]:
                self.best_position[i] = self.group_position[i]
            self.eval[i] = temp_eval[i]
            if temp_eval[i] < self.best_position_globe_value:
                self.best_position_globe_value = temp_eval[i]
                self.best_position_globe = self.group_position[i]
            print(f"第{i + 1}号个体的")
            print(f"当前位置为:{self.group_position[i]}\n局部最佳位置为:{self.best_position[i]}\n速度为:{self.group_speed[i]}\n适应值为:{self.eval[i]}")
        print(f"全局最佳位置为:{self.best_position_globe}, 全局最佳适应值为:{self.best_position_globe_value}")

    def train(self, iter_num=50):
        self.group_speed, self.group_position = self.initialize()
        for iter in range(iter_num):
            print(f"--------------------------开始第{iter+1}轮训练---------------------------")
            self.update()
            self.evaluate()


if __name__ == '__main__':
    pso = PSO(5, 4)
    pso.train(iter_num=500)


  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

火锅店的保安长

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

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

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

打赏作者

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

抵扣说明:

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

余额充值