[文章目录]
Description
某加工厂有A、B两台机器,来加工的产品可以由其中任何一台机器完成,或者两台机器共同完成。由于受到机器性能和产品特性的限制,不同的机器加工同一产品所需的时间会不同,若同时由两台机器共同进行加工,所完成任务又会不同。某一天,加工厂接到n个产品加工的任务,每个任务的工作量不尽一样。你的任务就是:已知每个任务在A机器上加工所需的时间t1, B机器上加工所需的时间t2及由两台机器共同加工所需的时间t3,请你合理安排任务的调度顺序,使完成所有n个任务的总时间最少。
朴素dp:dp[i][j][k]表示第i份任务A机器工作了j小时,B机器工作了k小时是否可达。将状态和值换一下:dp[i][j]表示第i个物品,A机器工作j小时时B机器最小工作时长。那么答案就是max(j,dp[n][j]),然后循环数组。
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
#define rint register int
int read()
{
int re=0; char ch=getchar();
while(ch<'0'||ch>'9') ch=getchar();
while(ch>='0'&&ch<='9')
re=(re<<1)+(re<<3)+ch-'0',ch=getchar();
return re;
}
int n,ans=1<<30;
int dp[2][30010];
int main()
{
n=read();
memset(dp,0x3f,sizeof dp);
dp[0][0]=0;
register bool flag=1;
rint x,y,z;
for(rint i=1;i<=n;++i)
{
x=read(); y=read(); z=read();
for(rint j=0;j<=30000;++j)
{
dp[flag][j]=0x3f3f3f3f;
if(x&&j-x>=0) dp[flag][j]=min(dp[flag][j],dp[flag^1][j-x]);
if(y) dp[flag][j]=min(dp[flag][j],dp[flag^1][j]+y);
if(z&&j-z>=0) dp[flag][j]=min(dp[flag][j],dp[flag^1][j-z]+z);
}
flag^=1;
}
flag^=1;
for(rint i=0;i<=30000;++i)
ans=min(ans,max(dp[flag][i],i));
printf("%d",ans);
return 0;
}