一、动态规划(Dynamic programming )

分析过程:

  1. 识别子问题 sub-problems dividing
  2. 识别子问题中的重叠特点 over-lapping sub-problem
  3. 存储子问题的答案 cache sub-solutions
  4. 合并问题答案 combine solutions
  5. 解析答案 parse solutions

问题:木头价格如下
[1, 5, 8, 9, 10, 17, 17, 20, 24, 30, 33] 下表加一为米数,值为价格
给出一段木头的长度,怎么切分价格最高?

"""
Cutting Problem

All the dynamic programming:
1. sub-problems
2. Overlapping sub-problems
3. parse solution
"""

from collections import defaultdict
from functools import lru_cache
# least recent used

prices = [1, 5, 8, 9, 10, 17, 17, 20, 24, 30, 33]
complete_price = defaultdict(int)
for i, p in enumerate(prices): complete_price[i+1] = p

solution = {}

cache = {}
#<- if when n .... is huge. size(cache)
# keep most important information.


@lru_cache(maxsize=2**10)
def r(n):
    # a very classical dynamic programming problem
    # if n in cache: return cache[n]

    candidates = [(complete_price[n], (n, 0))] + \
                 [(r(i) + r(n-i), (i, n - i)) for i in range(1, n)]

    optimal_price, split = max(candidates)

    solution[n] = split

    # cache[n] = optimal_price

    return optimal_price


def parse_solution(n, cut_solution):
    left, right = cut_solution[n]

    if left == 0 or right == 0: return [left+right, ]
    else:
        return parse_solution(left, cut_solution) + parse_solution(right, cut_solution)


if __name__ == '__main__':
    print(r(19))
    print(solution)
    print(parse_solution(19, solution))

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值