2020-02-24:arr是面值数组,其中的值都是正数且没有重复。再给定一个正数aim。每个值都认为是一种面值,且认为张数是无限的。返回组成aim的最少货币数。
福哥答案2020-02-24:
自然智慧即可。
1.递归。有代码。
2.动态规划。dp是二维数组。有代码。
代码用golang编写,代码如下:
package main
import (
"fmt"
)
func main() {
arr := []int{1, 2, 3}
aim := 8
ret := minCoins1(arr, aim)
fmt.Println("1.递归:", ret)
ret = minCoins2(arr, aim)
fmt.Println("2.动态规划:", ret)
}
const INT_MAX = int(^uint(0) >> 1)
func minCoins1(arr []int, aim int) int {
return process1(arr, 0, aim)
}
func process1(arr []int, index int, rest int) int {
if index == len(arr) {
if rest == 0 {
return 0
} else {
return INT_MAX
}
} else {
ans := INT_MAX
for zhang := 0; zhang*arr[index] <= rest; zhang++ {
next := process1(arr, index+1, rest-zhang*arr[index])
if next != INT_MAX {
if ans > zhang+next {
ans = zhang + next
}
}
}
return ans
}
}
func minCoins2(arr []int, aim int) int {
if aim == 0 {
return 0
}
N := len(arr)
dp := make([][]int, N+1)
for i := 0; i < N+1; i++ {
dp[i] = make([]int, aim+1)
}
dp[N][0] = 0
for j := 1; j <= aim; j++ {
dp[N][j] = INT_MAX
}
for index := N - 1; index >= 0; index-- {
for rest := 0; rest <= aim; rest++ {
dp[index][rest] = dp[index+1][rest]
if rest-arr[index] >= 0 && dp[index][rest-arr[index]] != INT_MAX {
dp[index][rest] = getMin(dp[index][rest], dp[index][rest-arr[index]]+1)
}
}
}
return dp[0][aim]
}
func getMin(a int, b int) int {
if a < b {
return a
} else {
return b
}
}
执行结果如下:
公众号:福大大架构师每日一题
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
· 开发者必知的日志记录最佳实践
· winform 绘制太阳,地球,月球 运作规律
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· AI 智能体引爆开源社区「GitHub 热点速览」
· Manus的开源复刻OpenManus初探
· 写一个简单的SQL生成工具