3252 - 偷天换日

神偷对艺术馆内的名画垂涎欲滴准备大捞一把。艺术馆由若干个展览厅和若干条走廊组成。每一条走廊的尽头不是通向一个展览厅,就是分为两个走廊。每个展览厅内都有若干幅画,每副画都有一个价值。经过走廊和偷画都是要耗费时间的。警察会在第n秒到达进口,在不被逮捕的情况下你最多能得到的价值。

题目输入

第一行一个整数 n
第二行若干组整数,对于每组整数(t,x),t表示进入这个展览厅或经过走廊要耗费t秒的时间,若x>0表示走廊通向的展览厅内有x幅画,接下来x对整数(w,c)表示偷一幅价值为w的画需要c秒的时间。若x=0表示走廊一分为二。
输入是按深度优先给出的。

题目输出

仅一个整数,表示能获得的最大价值。

输入/输出样例

题目输入

50
5 0 10 1 10 1 5 0 10 2 500 1 1000 2 18 1 1000000 4

题目输出

1500

提示

Hint
n≤600;t,c≤5;x≤30
房间和走廊数不超过300个。
注意题目要求你在的情况下得到最多的价值 不被逮捕

样例的输入对应于下图

<img src="http://tk.hustoj.com:80/attached/image/20141017/20141017112948_50179.png" alt="" />

C++解答

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
int n,m,v,x,y,k,l,num;
int a[301][3];
int f[301][601];
int t[301];
int m_max(int x,int y)
{
	if(x>y) return x;
	else return y;
}
void init(int);
void treedp(int);
int main()
{
	//freopen("steal.in","r",stdin);
	//freopen("steal111.out","w",stdout);
	cin>>v;
	num=1;
	init(1);
	
	treedp(1);
	cout<<f[1][v-1]<<endl;
	return 0;
}
void init(int now)
{
	cin>>t[now]>>k;
	if(k==0)
	{
		num++;
		a[now][1]=num;
		init(num);
		num++;
		a[now][2]=num;
		init(num);
	}
	else
	{
		for(int i=1;i<=k;i++)
		{
			cin>>x>>y;
			for(int j=v;j>=t[now]+t[now]+y;j--)
			{
				f[now][j]=max(f[now][j],f[now][j-y]+x);
			//	cout<<"f["<<now<<"]["<<j<<"]="<<f[now][j]<<' ';
			}
			//cout<<endl;	
		}
	}
}
void treedp(int now)
{
	if(a[now][1]+a[now][2]==0) return;
	treedp(a[now][1]);
	treedp(a[now][2]);
	for(int i=0;i<=v;i++)
		for(int j=i-t[now]-t[now];j>=0;j--)
		f[now][i]=max(f[now][i],f[a[now][1]][j]+f[a[now][2]][i-j-t[now]-t[now]]);
}

提示

Hint
n≤600;t,c≤5;x≤30
房间和走廊数不超过300个。
注意题目要求你在的情况下得到最多的价值 不被逮捕

样例的输入对应于下图

<img src="http://tk.hustoj.com:80/attached/image/20141017/20141017112948_50179.png" alt="" />

时间限制 1 秒
内存限制 128 MB
讨论 统计
上一题 下一题