codeforces 893D - Credit Card (贪心)

本文解析 Codeforces 893D 的信用卡管理问题,介绍如何判断是否能避免透支及确定最小补款次数的方法,并提供 C 语言实现代码。

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

传送门codeforces 893D



题目大意

有一张信用卡,初始金额为 0. 每天都有交易额 a[i],每天早上可以去银行补充任意金额(正数)的钱,每天晚上需要进行以下操作:


1. a[i]>0 时,往信用卡里存入 a[i] 的钱

2. a[i]<0 时,从信用卡里取出 a[i] 的钱

3. a[i]=0 时,核对信用卡里的钱


要求信用卡里的钱数不得超过上限 d,如果一定超过上限 d 则输出 -1 。每次核对的时候银行卡里的钱不得为负数,问最少需要去银行补充多少次钱。



思路

先考虑输出 -1 的情况,也就是只满足最低要求的情况下,如果信用卡里的钱还会超过 d,则输出 -1. 注意由于要求每次核对时信用卡里的钱不得为负数,所以每次核对时如果信用卡里的钱为负值,则置为 0.


然后考虑最少去银行补充几次钱。很明显,银行卡里的钱越多,需要补充的次数就越少,最多为上限 d。但是这样又会出现新的问题:如果当前信用卡里的钱为 d,而接下来的交易额为正数的话则就超过上限了,不符合题意。所以,如果信用卡里的钱大于 d 的时候应该将钱置为 d。



代码

#include<stdio.h>
#include<string.h>
int main()
{
	int i,n,d,f,sum,ans,a[100010];
	while(~scanf("%d%d",&n,&d))
	{
		f=sum=0;
		for(i=0;i<n;i++)
		{ //输入交易额并判断是否会超过上限 
			scanf("%d",&a[i]);
			sum+=a[i];
			//如果核对时钱小于 0,则置为 0 
			if(a[i]==0&&sum<0) sum=0;
			if(sum>d) f=1; //超过上限 
		}
		if(f) printf("-1\n");
		else
		{
			ans=sum=0;
			for(i=0;i<n;i++)
			{ //求最少补充钱的次数 
				sum+=a[i];
				if(sum>d) sum=d; //如果当前钱大于上限则置为 d				
				if(a[i]==0)
				{ //核对 
					if(sum<0)
					{ //如果钱为负数则结果 +1 
						ans++;
						sum=d; //将信用卡内的钱补充到最大 
					}
				}
			}
			printf("%d\n",ans);
		}
	}
	return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值