题目链接:
http://codeforces.com/contest/864/problem/E
题解:
简单的01背包,加一个DFS。
代码:
#include <cmath>
#include <vector>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std;
#define inf 0x3f3f3f3f
#define met(a,b) memset(a,b,sizeof(a))
const int maxn = 100+10;
vector<int> p;
int dp[maxn][2010];
int ans[maxn][2010];
struct node
{
int t,d,p;
int pos;
}num[maxn];
int cmp(node a,node b)
{
return a.d<b.d;
}
int main()
{
int n;
scanf("%d",&n);
for(int i=1;i<=n;i++)
{
int t,d,p;
scanf("%d%d%d",&t,&d,&p);
num[i].t=t;
num[i].d=d;
num[i].p=p;
num[i].pos=i;
}
met(dp,0);
met(ans,0);
sort(num+1,num+1+n,cmp);
for(int i=1;i<=n;i++)
{
for(int j=1;j<=2000;j++)
{
dp[i][j]=dp[i-1][j];
if(j>=num[i].t&&j<num[i].d)
{
if(dp[i-1][j-num[i].t]+num[i].p>dp[i][j])
{
dp[i][j]=dp[i-1][j-num[i].t]+num[i].p;
ans[i][j]=i;
}
}
}
}
int MAX=-inf,pos=0;
for(int i=1;i<=2000;i++)
{
if(dp[n][i]>MAX)
{
MAX=dp[n][i];
pos=i;
}
}
printf("%d\n",MAX);
int limit=n;
vector<int>p;
while(pos>0&&limit>0)
{
if(ans[limit][pos]>0)
p.push_back(num[ans[limit][pos]].pos);
pos-=num[ans[limit][pos]].t;
limit--;
}
printf("%d\n",(int)p.size());
reverse(p.begin(),p.end());
for(int i=0;i<p.size();i++)
{
if(i!=p.size()-1)
printf("%d ",p[i]);
else
printf("%d\n",p[i]);
}
}