不知道为什么一个大一的萌新能有这么多事要干......蚁群算法的代码先缓一缓,等博主写完作业,考完英语期中再说吧。关于遗传算法的代码,由于忘记了np数组不copy的时候会直接引用,导致很长一段时间不知道自己哪里出bug了,调了半天才想出来。所以大家学python的时候一定要打好基础呀~~下面是遗传算法的代码:

from math import *
from random import *
import numpy as np
import matplotlib.pyplot as plt

#遗传算法步骤
f=lambda x:x+10*np.sin(5*x)+7*np.cos(4*x)

#绘制函数图像,读者可自行去掉#号查看
x0=np.linspace(0,10,50000)
y0=f(x0)
#plt.figure()
#plt.plot(x0,y0)
#plt.show()

#初始参数
num=100 #种群数量
n=20 #DNA长度
pc=0.6 #交叉互换概率
pm=0.001 #变异概率
G=100 #最大代数
adaption=0.01 #适应度补充值

x=[i for i in range(0,101)] #代数,即迭代次数
y=[] #历代最优值
a=0 #下界
b=10 #上界
lis=[] #种群集

#1.选取初始种群
for i in range(num):
    lis.append(np.random.randint(2,size=n))
    #产生num个随机的DNA,只用两种碱基

for generation in range(G):
    #2.解码
    lis0=[] #个体函数值集
    for k in lis:
        s=0
        for j in range(n):
            s+=k[j]*2**(n-1-j)
        lis0.append(f(a+s*(b-a)/(2**n)))
    
    #3.适应度计算
    minlis=min(lis0)
    maxlis=max(lis0)
    y.append(maxlis)
    top=lis0.index(maxlis)
    ad_lis=[] #适应度集
    for i in range(num):
        ad_lis.append(lis0[i]-minlis+adaption)
    sum_ad=sum(ad_lis)
    for i in range(num):
        ad_lis[i]=ad_lis[i]/sum_ad
        
    #4.物竞天择
    #先计算部分和方便使用轮盘法
    ad_k=[] #适应度部分和序列
    optlis=[] #储存物竞天择后的个体
    for i in range(num):
        ad_k.append(sum(ad_lis[0:i+1]))
    for i in range(num-1):#物竞天择,但是留出一个位置给父辈的最优者
        p=random()
        for j in range(num):
            if p<ad_k[j]:
                opt=j
                break
        optlis.append(lis[opt].copy())
        #lis[opt]是对lis中的数组的引用!!
        #这里如果不使用copy,后面对optlis进行修改时也会带动lis的修改!!!

    #5.繁衍后代
    #先交叉互换,然后变异
    newlis=[]
    for i in range(0,num-1):
        A=optlis[i]#父本
        l=randint(0,98)
        B=optlis[l]#母本
        for j in range(0,n):
            p1=random()
            if p1<pc:
                A[j]=B[j] #交叉互换
        newlis.append(A.copy())
    
    for i in range(0,num-1):
        C=newlis[i]
        for j in range(0,n):
            p2=random()
            if p2<pm:
                C[j]=1-C[j] #变异
    newlis.append(lis[top].copy())

    #6.重复进化
    lis=newlis
    #将上面的步骤重复G次,即繁衍G代

lis0=[] #清空上一代函数值,准备做最后的处理
x1=[] #最后一代x值集合   
for k in lis:
    s=0
    for i in range(n):
        s+=k[i]*2**(n-1-i)
    x1.append(a+s*(b-a)/(2**n)) #记录最后一代的x值
    lis0.append(f(a+s*(b-a)/(2**n))) #记录最后一代的y值
y.append(max(lis0)) #将最后一代的最优值储存
top=lis0.index(max(lis0))
print([x1[top],max(lis0)]) #输出最优x值和y值

#绘制图像
yc=[max(y0) for i in range(len(y))]
plt.figure()
plt.plot(x,y,'b-',label='GA')
plt.plot(x,yc,'r-',label='max(f)')
plt.legend()
plt.show()

下面是原函数图像:

python脚本编写遗传算法 python遗传算法代码_遗传算法

下面是算法的迭代过程,做了多次,选择其中两次进行参考: 

python脚本编写遗传算法 python遗传算法代码_算法_02

python脚本编写遗传算法 python遗传算法代码_python脚本编写遗传算法_03

        不难看出来遗传算法的收敛速度还是挺快的~~若要了解遗传算法的原理,请移步至博主的另一篇短文《遗传算法原理》。