动态规划:
我们设计状态$f[i][j]$表示第$i$时刻,能力值为$j$能滑雪的最多次数
预处理出:
$a[i][j]$表示以$i$这个时刻结束,能力值为$j$时最晚的滑雪课开始时间
$les[i]$表示至少需要能力为$i$的最短滑雪时间
$g[i]$表示$i$时刻能滑雪的最多次数
状态转移:
$f[i][j]=f[i-1][j]$ //喝可可,什么都不做。。
$f[i][j]=max(f[i][j],g[a[i-1][j]])$ //上课,那么$f[i][j]$就是开始时间滑雪最多次数
$f[i][j]=max(f[i][j],f[i-les[j]][j]+1)$ //滑雪,那么现在的值就是$i-les[j]$时刻最大值$+1$
更新$g$数组
代码:
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#define N 10007
#define M 107
using namespace std;
int t,s,n;
int f[N][M],a[N][M],g[N],les[N];
int main()
{
	scanf("%d%d%d",&t,&s,&n);
	for(int i=1;i<=s;++i)
	{
		int in1,in2,in3;
		scanf("%d%d%d",&in1,&in2,&in3);
		a[in1+in2-1][in3]=max(a[in1+in2-1][in3],in1);
	}
	memset(les,0x3f,sizeof(les));
	for(int i=1;i<=n;++i)
	{
		int in1,in2;
		scanf("%d%d",&in1,&in2);
		for(int j=in1;j<=100;++j)
			les[j]=min(les[j],in2);
	}
	memset(f,0xcf,sizeof(f));
	f[0][1]=0;
	for(int i=1;i<=t;++i)
	{
		for(int j=1;j<=100;++j)
		{
			f[i][j]=f[i-1][j];
			if(a[i-1][j])
				f[i][j]=max(f[i][j],g[a[i-1][j]]);
			if(i-les[j]>=0)
				f[i][j]=max(f[i][j],f[i-les[j]][j]+1);
			g[i]=max(g[i],f[i][j]);
		}
	}
	printf("%d",g[t]);
	return 0;
}
原文:https://www.cnblogs.com/yexinqwq/p/10211627.html