1.1 自话粒子群

来源:互联网 发布:万云网络 编辑:程序博客网 时间:2024/06/11 05:35
简介
        上次在自话遗传算法中提到后期会写两篇关于粒子群算法和蚁群算法的博文,所以这次给大家带来的是我对粒子群的一些理解,并附带一个相当简单的实例去描述这个算法,我会尽力通俗易懂的把整个算法描述一遍,其实粒子群算法的思想也挺简单的,希望我不要反而写复杂了,下面同样引用百度百科的摘要结束简介部分。
粒子群优化算法(PSO)是一种进化计算技术(evolutionary computation),1995 年由Eberhart 博士和kennedy 博士提出,源于对鸟群捕食的行为研究 。该算法最初是受到飞鸟集群活动的规律性启发,进而利用群体智能建立的一个简化模型。粒子群算法在对动物集群活动行为观察基础上,利用群体中的个体对信息的共享使整个群体的运动在问题求解空间中产生从无序到有序的演化过程,从而获得最优解。
基本思想
正如简介所描述的那样,粒子群算法是模拟群体智能所建立起来的一种优化算法,像后面我向大家介绍的蚁群算法也属于这类算法,粒子群算法可以用鸟类在一个空间内随机觅食为例,所有的鸟都不知道食物具体在哪里,但是他们知道大概距离多远,最简单有效的方法就是搜寻目前离食物最近的鸟的周围区域。
所以,粒子群算法就是把鸟看成一个个粒子,并且他们拥有位置和速度这两个属性,然后根据自身已经找到的离食物最近的解和参考整个共享于整个集群中找到的最近的解去改变自己的飞行方向,最后我们会发现,整个集群大致向同一个地方聚集。而这个地方是离食物最近的区域,条件好的话就会找到食物。这就是粒子群算法,很好理解。
算法描述
所以,我们需要一个pbest来记录个体搜索到的最优解,用gbest来记录整个群体在一次迭代中搜索到的最优解。速度和粒子位置的更新公式如下:

v[i] = w * v[i] + c1 * rand() * (pbest[i] - present[i]) + c2 * rand() * (gbest - present[i]) present[i] = present[i] + v[i] 


其中v[i]代表第i个粒子的速度,w代表惯性权值,c1和c2表示学习参数,rand()表示在0-1之间的随机数,pbest[i]代表第i个粒子搜索到的最优值,gbest代表整个集群搜索到的最优值,present[i]代表第i个粒子的当前位置。
我这里打了一个求解y=-x*(x-1) 在[-2,2]上最大值的粒子群算法,选用这个简单的例子主要是能让大家清楚的看到效果和粒子的运动方向,也方便理解我想说的一些观点。代码如下:

[java] view plaincopyprint?<span style="font-family:Microsoft YaHei">/*** * 计算y=-x(x-1)的最大值 * 取值范围x--[-2,2] * @author BreezeDust * */ public class PSOTest { int n=2; //粒子个数,这里为了方便演示,我们只取两个,观察其运动方向 double[] y; double[] x; double[] v; double c1=2; double c2=2; double pbest[]; double gbest; double vmax=0.1; public void fitnessFunction(){//适应函数 for(int i=0;i<n;i++){ y[i]=-1*x[i]*(x[i]-2); } } public void init(){ //初始化 x=new double[n]; v=new double[n]; y=new double[n]; pbest=new double[n]; /*** * 本来是应该随机产生的,为了方便演示,我这里手动随机落两个点,分别落在最大值两边 */ x[0]=-0.5; x[1]=2.6; v[0]=0.01; v[1]=0.02; fitnessFunction(); //初始化当前个体极值,并找到群体极值 for(int i=0;i<n;i++){ pbest[i]=y[i]; if(y[i]>gbest) gbest=y[i]; } System.out.println("start gbest:"+gbest); } public double getMAX(double a,double b){ return a>b?a:b; } //粒子群算法 public void PSO(int max){ for(int i=0;i<max;i++){ double w=0.4; for(int j=0;j<n;j++){ //更新位置和速度 v[j]=w*v[j]+c1*Math.random()*(pbest[j]-x[j])+c2*Math.random()*(gbest-x[j]); if(v[j]>vmax) v[j]=vmax; x[j]+=v[j]; //越界判断 if(x[j]>2) x[j]=2; if(x[j]<-2) x[j]=-2; } fitnessFunction(); //更新个体极值和群体极值 for(int j=0;j<n;j++){ pbest[j]=getMAX(y[j],pbest[j]); if(pbest[j]>gbest) gbest=pbest[j]; System.out.println(x[j]+" "+v[j]); } System.out.println("======"+(i+1)+"======gbest:"+gbest); } } public static void main(String[] args){ PSOTest ts=new PSOTest(); ts.init(); ts.PSO(100); } }</span> 


输出结果如下:

[plain] view plaincopyprint?<span style="font-family:Microsoft YaHei">start gbest:0.0 -0.4 0.1 0.0 -10.751668729351186 ======1======gbest:0.0 -0.6822365786740794 -0.2822365786740793 0.0 -5.375834364675593 ======2======gbest:0.0 -0.5822365786740794 0.1 0.0 -2.6879171823377965 ======3======gbest:0.0 -0.48223657867407943 0.1 -1.3439585911688983 -1.3439585911688983 ======4======gbest:0.0 -0.38223657867407945 0.1 -1.2439585911688982 0.1 ======5======gbest:0.0 -0.47659030560462123 -0.09435372693054181 -1.143958591168898 0.1 ======6======gbest:0.0 -0.37659030560462126 0.1 -1.043958591168898 0.1 ======7======gbest:0.0 -0.2765903056046213 0.1 -0.943958591168898 0.1 ======8======gbest:0.0 -0.27903394174424034 -0.0024436361396190653 -0.843958591168898 0.1 ======9======gbest:0.0 -0.38899022876058803 -0.10995628701634769 -0.7439585911688981 0.1 ======10======gbest:0.0 -0.35250959144436234 0.03648063731622572 -0.6439585911688981 0.1 ======11======gbest:0.0 ........ ........ ........ ........ 0.9999990975760489 -1.556071309835406E-6 ======98======gbest:1.0 1.0000000029937202 4.411275849326098E-9 1.0000001827158205 1.085139771533034E-6 ======99======gbest:1.0 0.9999999993730952 -3.6206249540206964E-9 1.0000001197322141 -6.298360633295484E-8 ======100======gbest:1.0</span> 



我们可以从打印的数据看出来,刚开始x[0]和x[1]分散在最大值两边,然后x[0]和x[1]逐渐聚集到1的周围,这里,我们已经收敛到x=1这个地方了,这正是我们要求的最大值,其最大值为1,下面是图解过程。
1.初始状态

2.第二次x[1]向左边移动了

3.最后,两点聚集在1上,上面多个圈是他们聚集的过程,可以看出来,聚集过程是个越来越密集的过程。



最后
粒子群算法,相对于我上次提到的遗传算法而言编码要简单很多,同样属于进化算法,但是粒子群算法并没有像遗传算法那样有选择交叉变异这样的过程,而更多的是体现在追踪单个粒子和共享集体最优信息来实现向最优空间搜索的形式,但是正由于它不同于遗传算法那样去忽略个体的一些内在联系,所以往往会陷入局部最优,所以,在粒子群算法中加入像遗传算法中的变异或者模拟退火等,可以跳过这个局部最优解。
而惯性权值对于函数收敛速度和是否收敛有很大的决定作用,两个学习参数c1,c2的制定也同等重要,但是即使这样,它也没有遗传算法中会有多个参数去维护,所以整个算法就那一个公式就行了,相当的清晰。在遗传算法中的信息的共享是染色体互相之间通过交叉共享,所以在搜索移动过程显得平均缓慢,而粒子群算法是根据gbest来决定整个集群的单向移动,所以相对遗传算法,它更快的收敛。
这不由得让我想到了熵这个概念,在诸如我们社会甚至宇宙这样复杂的系统,我们都处于一个无序的状态,属于熵增状态,像粒子群,遗传算法,对群体的研究,体现的智能不就是在这个无序的系统提供有序的能量,然后它就逐渐有序了。对于智能,我想我有更深的体会了。这段话属于发神经,不作参考。
0 0
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 华为梅特10忘记账号密码怎么办 华为荣耀8充电接口坏了怎么办 华为手机锁屏了自动开屏怎么办 支付宝收货地址写错了怎么办 支付宝领海报地址写错了怎么办 手机总是弹出日历已停止运行怎么办 华为mate8忘了锁屏密码怎么办 红米4a打王者卡怎么办 苹果5s软件更新密码忘记了怎么办 华为荣耀P9进水了没有声音怎么办 华为荣耀7原相机不能拍照怎么办 华为手机触屏密码忘记了怎么办 华为荣耀10屏锁密码忘了怎么办 华为手机开机卡在开机界面怎么办 苹果6s国行不能用移动4g怎么办 苹果手机32g内存不够用怎么办 华为荣耀6x忘记了密码怎么办 百度粉色衣服被洗变色了怎么办 粉色衣服放进洗衣机洗变色了怎么办 红米note5a应用锁忘了怎么办 索尼手机死机了怎么办不可拆卸电池 华为手机一直停留在开机画面怎么办 5s用11.4太卡了怎么办 华为荣耀5a手机声音小怎么办 牙签卡在手机插卡针里怎么办 捡的华为手机账号激活不了怎么办 华为平板激活手机密码忘了怎么办 捡个华为手机非要激活才能用怎么办 华为手机没激活想重新激活怎么办 华为手机激活总显示系统繁忙怎么办 华为荣耀7i进水了不开机怎么办 华为荣耀手机进水了怎么办开不开机 华为畅享5s变砖怎么办 我的苹果7机身内存满了怎么办 小米5x拆机后屏幕翘边怎么办 苹果手机设备禁止游戏登入怎么办 苹果7plus玩游戏掉频怎么办 孕期牙套子掉了基牙烂掉了怎么办 美团绑定的信用卡过期了怎么办 苹果6s手机开不开机怎么办 换了散热硅胶后还是死机怎么办