算法实现之问题求解

货郎担问题

一个的组合优化问题,目标是在给定的一组城市和城市间的距离数据下,寻找一条最短路径,使得每个城市恰好访问一次,并最后回到起始城市。

python实现(动态规划):

import sys

def tsp(graph, curr_city, visited, n, count, path, ans, min_dist):
    if count == n and graph[curr_city][0]:
        ans.append(path.copy())
        min_dist[0] = min(min_dist[0], path[n-1][0] + graph[curr_city][0])
        return
    
    for i in range(n):
        if visited[i] == False and graph[curr_city][i]:
            visited[i] = True
            path.append((graph[curr_city][i], i))
            tsp(graph, i, visited, n, count+1, path, ans, min_dist)
            visited[i] = False
            path.pop()

def solve_tsp(graph):
    n = len(graph)
    visited = [False] * n
    visited[0] = True
    path = [(0, 0)]
    ans = []
    min_dist = [sys.maxsize]
    
    tsp(graph, 0, visited, n, 1, path, ans, min_dist)
    
    return ans, min_dist[0]
graph = [
    [0, 10, 15, 20],
    [10, 0, 35, 25],
    [15, 35, 0, 30],
    [20, 25, 30, 0]
]
solve_tsp(graph)

连续邮资问题

一种组合优化问题,给定一系列不同面值的邮票,如何用最少的邮票凑出给定的邮资金额。

python实现(回溯法):

def func(postage, stamps):
    result = float('inf') 
    path = [] 

    def dfs(remaining):
        nonlocal result
        if remaining == 0: # 当前路径组合的邮资金额等于所需金额
            result = min(result, len(path))
            return

        for stamp in stamps:
            if remaining >= stamp and len(path) < result:
                path.append(stamp) # 尝试将当前面值的邮票加入路径
                dfs(remaining - stamp) # 继续向下递归
                path.pop() # 回溯,将当前尝试的邮票移出路径

    dfs(postage)
    if result == float('inf'):
        return 0
    return result

postage = 18
stamps = [1, 5, 10] # 邮票面值
result = func(postage, stamps)
print(f"使用{result}张邮票凑出邮资金额{postage}")

python实现(动态规划):

def func(postage, stamps):
    dp = [float('inf')] * (postage + 1) 
    dp[0] = 0 

    for i in range(1, postage + 1):
        for stamp in stamps:
            if i >= stamp:
                dp[i] = min(dp[i], 1 + dp[i - stamp]) # 动态规划求解最优解

    if dp[postage] == float('inf'):
        return "无法凑出该邮资金额"
    else:
        return dp[postage]

# 示例使用
postage = 18
stamps = [1, 5, 10] # 邮票面值
result = func(postage, stamps)
print(f"需要最少使用{result}张邮票凑出邮资金额{postage}")

本文仅为学习记录,如有错误欢迎指出。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值