实验8 分布估计算法求解背包问题

240 阅读4分钟

传送门(所有的实验都使用python实现)

实验1 BP神经网络实验

实验2 som网实验

实验3 hopfield实现八皇后问题

实验4 模糊搜索算法预测薄冰厚度

实验5 遗传算法求解tsp问题

实验6 蚁群算法求解tsp问题

实验7 粒子群优化算法求解tsp问题

实验8 分布估计算法求解背包问题

实验9 模拟退火算法求解背包问题

实验10 禁忌搜索算法求解tsp问题

 

一、实验目的

理解并使用分布估计算法

二、实验内容

实现基于分布估计算法的背包问题求解

三、实验环境

使用Python3.0 在 eclipse进行编辑

四、实验步骤

1、输入介绍:

    背包物体的个数为10,背包容量C,物品价值p,物品重量c。初始化概率模型每维为0.5

   

2、产生个体:

    通过概率模型,产生n个体。

 

3、计算个体适应度:

个体适应度为背包中物体的价值总和取负数,但是背包超重的情况下,方案不合法。所以加入罚函数,设超过部分重量为r,将适应值加上r^2*M,只要M足够大就可以将适应值大大降低,进而避免被当成较优解选中。

 

4、保留适应度较高的前x个解,通过计算联合概率分布,更新概率模型。

   

5.终止条件

    若全局最优未达到295,回到步骤2,否则打印结果,结束迭代。

 

 

 

运行截图:

 

 

个体数100,较优解取前30%。未找到最优解

个体数200,较优解取前30%。找到最优解

个体数500,较优解取前30%。找到最优解

个体数1000,较优解取前30%。找到最优解

五、总结

个体数直接影响了算法的效率,通过多次实验可以知道当个体数为100时,多次迭代未能找出最优解,陷入了局部最优,当个体数逐渐增多时,迭代次数明显减少。但是个体过多会导致单次迭代次数时间变长,所以个体数量在500为最佳。此外,构造概率模型的前x个较优解也会影响效率,x取太大失去了较优解的优势,取太小损失了部分较优解,所以取30%为最佳。

python源码

#coding:gbk
import random
global n,m,C;    #n个体数量, m物品数量 ,背包容量C
global bn,time;    # bn较优个体数量 time 迭代次数
global best;   #记录全局最优
n=100; m=10; bn=int(n*0.3);  
time =100; #控制迭代次数
p = [0.0]*m; ans = [[0]*(m) for i in range(n)] #概率模型p   ans记录种群情况 
F = [0.0]*n ;  best_way=[0]*m; #F个体适应值  best_way 记录全局最优解方案
weight=[95, 4, 60, 32, 23, 72, 80, 62,65, 46]; value=[55, 10, 47, 5, 4, 50, 8, 61,85, 87]

def cop(a,b,le):     #复制函数 把b数组的值赋值a数组
    for i in range(le):
        a[i]=b[i]
def produce():  #个体产生
    for i in range(n):
        for k in range(m):
            if(random.random() < p[k]):  ans[i][k]=1;
            else: ans[i][k]=0;
def calc(x):  #计算个体适应值
    global C
    vsum=0;wsum=0;
    for i in range(m):
        vsum +=x[i]*value[i];  wsum += x[i]*weight[i];
    if(C-wsum < 0):  gg=C-wsum;     #罚函数,若超重则会被无限放大
    else :gg= 0;
    return -vsum+10000*gg*gg;
def update():      #更新概率模型
    mx = -1; ob=0;
    for i in range(m): p[i]=0;
    for i in range(bn):
        mx = -1;
        for k in range(n): 
            if(-F[k]>mx): mx=-F[k]; ob=i;
        F[ob]=10000;
        for j in range(m): 
            if(ans[ob][j]==1):p[j]+=1.0;
    for i in range(m): 
            p[i]=p[i]/bn;        
def init():   #初始化函数
    global C,best;
    C = 269;
    best=-1;
    for i in range(m):p[i]=0.5; #初始概率都为0.5
    
def slove():  #迭代函数
    global best
    produce()    #产生新个体
    for i in range(n):  #计算适应度
        F[i]=calc(ans[i])
        if(-F[i] > best ):
            best = -F[i]; cop(best_way,ans[i],m);
    update();   #更新概率模型

init();
isGood = 0; #标记是否找到最优解

for i in range(time):      
    slove();
    if(best==295):  
        print('找到最优解:295,迭代次数',i+1); isGood = 1;  break;    #达到最优解提前退出
        
if(isGood == 0):   print('只找到次优解:',best,'迭代次数',time);
print('方案为:',best_way);               #打印方案

 

 

本文已参与「新人创作礼」活动,一起开启掘金创作之路