[U]3.1.6 Stamps 会错意的DP题

本文介绍了一种使用一维动态规划解决邮票问题的方法。初始采用的二维DP方案因空间和时间效率问题未能完全解决问题,后续改进为一维DP,显著提升了效率并成功解决了问题。文章详细展示了具体的实现过程。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

3章第一节有道题敲不出来啊~~~没办法,只能把后面的题先给敲咯~

这个题呢...

首先本巨菜想了一个很傻很水很烂的DP方程。使得自己的程序果断崩了...


开了一个10001*200的二维boolean数组,[面额][张数]这样来DP,因为最大的面额只有10000 ,再通过循环数组的方法,勉强使得空间不爆掉,结果过了9个点,第10个点果断超时。

后来牌桌子一想!可以变成一维DP!a[面额]保存的值为最小张数;

a[i]=min( a[i],a[i-面额]+1 );

这样就很好的A掉了。速度还行。

/*
ID:bysen
LANG:C++
PROG:stamps
*/
#include<stdio.h>
#define INF 0x0FFFFFFF
using namespace std;

int re[10001];
//DP数组记录构成当前面额最小的邮票枚数 
int v[201];

int min( int a,int b ){ return a<b?a:b; }

int main()
{
 	freopen( "stamps.in","r",stdin );
 	freopen( "stamps.out","w",stdout );
 	int k,n;
 	for( int i=0;i<10001;i++ )
 		 re[i]=INF;
 	
 	scanf( "%d %d",&k,&n );
 	
	for( int i=0;i<n;i++ )
	{
 		 scanf( "%d",&v[i] );
 		 re[v[i]]=1;
    }
    
    int top=v[0];
    while( true )
    {
	 	   top++;
	 	   if( top>10001 )
	 	   	   re[top%10001]=INF;
	 	   	   
	 	   for( int i=0;i<n;i++ )
	 	   		if( top-v[i]>0 )
	 	   			re[top%10001]=min( re[top%10001],re[(top-v[i]+10001)%10001]+1 );
	   		if( re[top%10001]>k )
	   			break;
    }
    printf( "%d\n",top-1 );
 	return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值