肝任务(中二羊)

肝任务(task.cpp)

题面

【题目描述】

众所周知,敢玩手机游戏的人不是氯金大佬(能充钱)就是绝世肝帝(大量时间在线)。ZEY最近迷上了一款手机游戏,当然,ZEY非常穷,只能投入大量时间来肝任务,尽管ZEY浑身是肝,但是面对阴险的游戏策划,他终于肝!不!动!了!
现在这款游戏又在周末搞活动了,要达成活动成就需要不低于 n 点活跃值,在活动期间有 k 种任务可以完成,每种任务都能够不断重复完成。不过ZEY看到这个活动已经恶心到想吐了,如果他的恶心程度超过 m 点,他就会晕倒!(那当然就不能继续完成活动任务了)另外,ZEY发现明天就是星期一,但是自己—点作业都没写,所以他最多还能玩 t 个时间单位的游戏。
已知完成第 i 个任务,可以获得 x[i] 点活跃值,但是ZEY也会增加 y[i]点恶心度,同时会消耗 1 点单位时间。现在,ZEY想知道自己能不能达成活动成就,如果能达成,他还想知道自己最多能有多不恶心(用 m 减去累计的恶心度);如果不能达成,他也想知道最多可以获得多少活跃值。

【输入说明】

输入文件名为task.in。输入为多行
第一行输入4个整数,分别是 k,n,m,t ,数字间用空格隔开
接下来k行,每—行输入两个整数,分别是 x[i]y[i]

【输出说明】

输出文件名为task.out。输出—行,分两种情况:

  1. 如果能达成活动成就,输出大写字母 Y 以及最大的不恶心程度,用空格隔开
  2. 如果不能达成活动成就,输出大写字母 N 以及最多的活跃值,用空格隔开

输入样例1:

1 5 5 5 5
1 1

输出样例1:

Y 0

输入样例2:

2 12 8 3
3 1
4 3

输入样例2:

N 11

【样例说明】

对于样例1,完成 5 次人物刚好达成成就,不恶心程度为 0
对于样例2,容易证明无法达成,当完成1次人物1或2次任务2时,活跃值最大为 11

【数据范围】

1,n,m,t1501xi,yi20

题解

题目考点:动态规划,动规,dp。背包。
背包特点:二维背包。
方程: dpj,p=max(dpj,p,dpj1,pkkki,1+kkki,0) 。其中 kkki,0 为活跃值(即 xi ), kkki,1 为恶心度(即 yi ), j 为时间, p 为恶心度。
翻译方程: 对于第 i 个活动:

  1. 做:
    dpj,p=dpj1,pkkki,1+kkki,0
  2. 不做:
    dpj,p=dpj,p

选择方案是选最大值,所以 dpj,p=max(dpj,p,dpj1,pkkki,1+kkki,0)
所以代码:

for(int i=1;i<=k;++i)
	for(int j=1;j<=t;++j)
		for(int p=kkk[i][1];p<=m;++p)
			dp[j][p]=max(dp[j][p],dp[j-1][p-kkk[i][1]]+kkk[i][0]);

但是题目要求求最不恶心程度,所以设置一个bool类型的变量来设置,如下:

bool fff=false;
/*循环代码跳过,方程跳过。*/
if(dp[j][p]>=n)fff=true,ans=max(ans,m-p);

这里求的是最不恶心程度的最大值,也可以求最恶心程度的最小值。即

ans=0x7f7f7f7f7f;
/*省略一些代码*/ans=min(ans,p);

输出: mans
然后就贴代码:

#include<iostream>
#include<cstdio>
using namespace std;
class QIO{
	public:
		inline int read(){
			x=0,f=1,ch=getchar();
			while(ch<'0'||ch>'9'){
				if(ch=='-')f=-f;
				ch=getchar();
			}
			while(ch>='0'&&ch<='9'){
				x=(x<<3)+(x<<1)+(ch^48);
				ch=getchar();
			}
			return x*f;
		}
		inline void write(int a){
			if(a<0)a=-a,putchar('-');
			output((unsigned int)a);
			}
	private:
		void output(unsigned int a){
			if(a>9)output(a/10);
			putchar((a%10)^48);
		}
		int x;
		short f;
		char ch;
};
QIO qrw;//快速输入输出
int kkk[200][2],dp[1001][1001];
signed main(){
	freopen("task.in","r",stdin);
	freopen("task.out","w",stdout);
	int k,n,m,t,ans=0;
	k=qrw.read();
	n=qrw.read();
	m=qrw.read();
	t=qrw.read();
	bool fff=false;
	for(int i=1;i<=k;++i){
		kkk[i][0]=qrw.read();
		kkk[i][1]=qrw.read();
	}
	for(int i=1;i<=k;++i)
		for(int j=1;j<=t;++j)
			for(int p=kkk[i][1];p<=m;++p){
				dp[j][p]=max(dp[j][p],dp[j-1][p-kkk[i][1]]+kkk[i][0]);
				if(dp[j][p]>=n)fff=true,ans=max(ans,m-p);
			}
	if(fff){
		putchar('Y');
		putchar(' ');
		qrw.write(ans);
	}else{
		putchar('N');
		putchar(' ');
		qrw.write(dp[t][m]);
	} 
	return 0;
}
posted @   SHOJYS  阅读(80)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· 没有Manus邀请码?试试免邀请码的MGX或者开源的OpenManus吧
· 【自荐】一款简洁、开源的在线白板工具 Drawnix
· 园子的第一款AI主题卫衣上架——"HELLO! HOW CAN I ASSIST YOU TODAY
· Docker 太简单,K8s 太复杂?w7panel 让容器管理更轻松!
点击右上角即可分享
微信分享提示