贪婪算法

贪婪算法:

在对问题求解时,总是做出在 当 前 看 来 是 最 好 的 选 择 。也就是说,不从整体最优上加以考虑,他所做出的仅是在某种意义上的局部最优解。贪心算法没有固定的算法框架,算法设计的关键是贪心策略的选择,贪心策略使用的前提是局部最优能导致全局最优。

设计过程:

1、建立数学模型来描述问题;
2、把求解的问题分成若干个子问题;
3、对每一子问题求解,得到子问题的局部最优解;
4、把所有子问题的局部最优解合成原始问题的一个解。

下面利用贪婪算法解决0-1背包问题:

[0-1背包问题] 有一个背包,背包容量是M=150kg。有7个物品,物品不可以分割成任意大小。
要求:尽可能让装入背包中的物品总价值最大,但不能超过总容量。

物品ABCDEFG
重量35kg30kg6kg50kg40kg10kg25kg
价值10403050354030

算法实现(Python 3):

"""
贪婪算法:
1) 贪婪算法不一定能得到全局最优解,贪婪得到的是局部最优解,最终结果取决于贪婪策略;
2) 贪婪算法的时间消耗比穷举法低很多;
3) 遗传算法在整个随机空间内搜索,效率低,训练慢,可以先使用贪婪算法生成遗传算法的初始化种群的个体,  
    以缩小搜索空间,加快训练时间。
"""

class Item(object):
    def __init__(self,n,v,w):
        self.name=n
        self.weight=float(w)
        self.value=float(v)

    def getName(self):
        return self.name

    def getValue(self):
        return self.value

    def getWeight(self):
        return self.weight

    def __str__(self):
        result = ' < '+self.name+' , '+str(self.value)+' , '+str(self.weight) + '>'
        return result

def value(item):
    return item.getValue()

def weight_inverse(item):
    return 1.0/item.getValue()

def density(item):
    return item.getValue()/item.getWeight()

def greedy(items,max_weight,key_function):
    items_order = sorted(items,key=key_function,reverse = True)
    result = []
    total_value = 0.0
    total_weight = 0.0
    for i in range(len(items_order)):
        if(total_weight + items_order[i].getWeight()) <= max_weight:
            result.append(items_order[i])
            total_value += items_order[i].getValue()
            total_weight += items_order[i].getWeight()
    return result,total_value

def build_item():
    names=['A','B','C','D','E','F','G']
    values = [35,30,6,50,40,10,25]
    weights=[10,40,30,50,35,40,30]
    Items=[]
    for i in range(len(names)):
        Items.append(Item(names[i],values[i],weights[i]))
    return Items

def greedy_run(items,constraint,key_function):
    taken,val=greedy(items,constraint,key_function)
    print ('Total value of items taken = ', val)
    for item in taken:
        print (' ', item)


if __name__ == '__main__' :
    items = build_item()

    print ('Use greedy by value to fill knapsack of size:')
    greedy_run(items, 150, value)

    print ('\n Use greedy by weight to fill knapsack of size:')
    greedy_run(items, 150, weight_inverse)

    print ('\n Use greedy by density to fill knapsack of size:')
    greedy_run(items, 150, density)

运行结果:

Use greedy by value to fill knapsack:
Total value of items taken =  155.0
   < D , 50.0 , 50.0>
   < E , 40.0 , 35.0>
   < A , 35.0 , 10.0>
   < B , 30.0 , 40.0>

 Use greedy by weight to fill knapsack:
Total value of items taken =  106.0
   < C , 6.0 , 30.0>
   < F , 10.0 , 40.0>
   < G , 25.0 , 30.0>
   < B , 30.0 , 40.0>
   < A , 35.0 , 10.0>

 Use greedy by density to fill knapsack:
Total value of items taken =  150.0
   < A , 35.0 , 10.0>
   < E , 40.0 , 35.0>
   < D , 50.0 , 50.0>
   < G , 25.0 , 30.0>
  • 0
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值