首页 > 其他分享 >1-1 硬币兑换

1-1 硬币兑换

时间:2024-03-01 19:55:31浏览次数:31  
标签:... min int 硬币 兑换 include 优化

本题是一个完全背包问题,需要对三重循环进行优化。
容易想到用(i, j)表示从前i个硬币中选取总价值为j的方案中,使用硬币数目的集合。f(i, j)表示其最小值。
则有 f(i, j) = min(f(i - 1, j - k*w[i]) + k), 其中 k = {0, 1, ..., j / w[i]},w[i]是第i个硬币的价值
于是本题在对i,j循环之外还要额外对k循环,一定会超时。需要进行优化。

我们发现,由
f(i, j) = min(f(i - 1, j - k*w[i]) + k), 其中 k = {0, 1, ..., j / w[i]} (1)

可得
f(i, j - w[i]) = min(f(i - 1, j - (k + 1)*w[i]) + k), 其中 k = {0, 1, ..., j / w[i]} (2)

把(2)代入(1),可得
f(i, j) = min(f(i - 1, j), f(i, j - w[i]) + 1)
优化完成

下面给出代码,使用滚动数组优化(不优化也能过)。

#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;

const int M = 25, N = 50010;

int f[N];
int w[M];

int main(){
	int n, m;
	cin>>n>>m;
	
	memset(f, 0x3f, sizeof f);
	f[0] = 0;
	
	for(int i = 1; i <= m; i++) cin>>w[i];
	
	for(int i = 1; i <= m; i++)
		for(int j = 1; j <= n; j++)
			if(j >= w[i]) f[j] = min(f[j], f[j - w[i]] + 1);
	
	cout<<f[n];
	
	return 0;
}

标签:...,min,int,硬币,兑换,include,优化
From: https://www.cnblogs.com/okljlwi/p/18047826

相关文章

  • day50 动态规划part7 代码随想录算法训练营 322. 零钱兑换【什么时候+1】
    题目:322.零钱兑换我的感悟:看着文字版也能做出来了,哈哈哈!!理解难点:这题是最小值dp[j]=min(dp[j],dp[j-coins[i]+1)因为是数量要加一个1,有的加,有的不加,还没太搞清楚。 听课笔记: 代码示例:classSolution:defcoinChange(self,coins:List[int],amount:int......
  • day44 动态规划part6 代码随想录算法训练营 518. 零钱兑换 II
    题目:518.零钱兑换II我的感悟:递推公式,我没写错。是初始化写错了。这种求多少种的,要考虑1种,是空集合选1中。而那些考虑能背最大的价值,要从0初始化,0的含义值无价值。 理解难点:递推公式,是累加dp[j]+=dp[j-conins[i]]初始化的含义 dp[0]=1听课笔记: 代码示例:cl......
  • P3706 「SDOI2017」硬币游戏 解题报告
    oj:https://gxyzoj.com/d/hzoj/p/P451概率与期望+hash+高斯消元声明一些东西,pre(S,l)表示串S的长度为l的前缀,lst(S,l)表示串S的长度为l的后缀一.对于所有串建立字典树,像「HNOI2013」游走一样高斯消元,时间复杂度\(O(n^3m^3)\),预计50/70pts二.正解:显然,n项中,出现一个长度......
  • 代码随想录 day44 零钱兑换 II 组合总和 Ⅳ
    零钱兑换II这里组合类问题用上了dp[j]=dp[j-nums[i]]这个递推式由于说了硬币可以用无数次也就是这是个完全背包问题这里先遍历物品再遍历背包就是算了组合数反过来就是算排列数组合总和Ⅳ这题就是组合类问题的排列数模板题......
  • P9238 [蓝桥杯 2023 省 A] 翻转硬币
    (题目传送门)受益良多啊……设\(f(i)\)表示第\(i\)枚硬币是否需要被翻转,以下所有运算均在模\(2\)意义下进行。初始化\(f(1)=1\),递推式有\(f(i)=\sum\limits_{d\midi,d\nei}f(d)\),答案即求\(\sum\limits_{i=1}^nf(i)\)。观察发现\(\sum\limits_{d\midi}f(d)=2f(i)=[......
  • 518. 零钱兑换 II(中)
    目录题目法一、回溯法二、动态规划题目给你一个整数数组coins表示不同面额的硬币,另给一个整数amount表示总金额。请你计算并返回可以凑成总金额的硬币组合数。如果任何硬币组合都无法凑出总金额,返回0。假设每一种面额的硬币有无限个。题目数据保证结果符合32位带符......
  • 322. 零钱兑换(中)
    目录题目法一、动态规划法二、带备忘录的动态规划法三、dp数组的迭代解法题目给你一个整数数组coins,表示不同面额的硬币;以及一个整数amount,表示总金额。计算并返回可以凑成总金额所需的最少的硬币个数。如果没有任何一种硬币组合能组成总金额,返回-1。你可以认为每种......
  • 441. 排列硬币
    441.排列硬币你总共有n枚硬币,并计划将它们按阶梯状排列。对于一个由k行组成的阶梯,其第i行必须正好有i枚硬币。阶梯的最后一行可能是不完整的。给你一个数字n,计算并返回可形成完整阶梯行的总行数。二分答案本题为一个还算简单的二分答案,我对二分答案的理解是:我......
  • 生活记录:和大师姐及实验室师兄弟一起吃鸡公煲留念——集积分兑换“毛绒玩具小猪”
    在实验室时每每出去聚餐吃饭总是喜欢去附近的鸡公煲,那家也是有个积分兑换毛绒玩具的活动,虽然最后也没有攒够积分而那家店在疫情中也没有熬过去,不过当年吃鸡公煲时是一直惦记着这个玩偶的,虽然未能实现自己的小目标但是这个经历还是蛮值得纪念的。   可爱的毛绒玩具——“小粉猪”......
  • 硬币找钱问题
    硬币找钱如题:思路:从最大币值入手include<stdio.h>intmain(){inta[6]={5,10,20,50,100,200};//币值,以分为单位intb[6];//存放对应硬币的个数intn;scanf("%d",&n);//输入n组测试数据while(n--){intj;//读取每种硬币的个数for(j......