2013腾讯编程马拉松初赛第〇场(3月20日) 吉哥系列故事——临时工计划---带权重的区间规划
Posted on 2013-07-29 20:07 冰天雪域 阅读(196) 评论(0) 编辑 收藏 举报题目:http://acm.hdu.edu.cn/showproblem.php?pid=4502
思路:带权重的区间规划问题,先将每个job按照完成时间进行排序,然后建立状态转移方程:OPT[I]=max{OPT[i-1],OPT[P[i]]+w[j]};其中P[i]代表与job i兼容的最大job下标。
代码:
#include <iostream> #include <algorithm> #include <cstring> #include <cstdlib> #include <cstdio> using namespace std; const int maxn=1005; int p[maxn]; int opt[maxn]; struct job{ int s,f; int w; }; job njob[maxn]; bool cmp(job a,job b) { return a.f<b.f; } bool iscompatible(job a,job b){ if(b.s>a.f || a.s>b.f)return 1; return 0; } void cal_p(int cnt) { p[1]=0; for(int i=cnt-1;i>1;i--) { int k=i-1; while(k>0 && !iscompatible(njob[i],njob[k])) k--; p[i]=k; } } int main() { int t; scanf("%d",&t); while(t--) { int m,n; scanf("%d%d",&m,&n); int cnt=1; for(int i=0;i<n;i++) { int sj,ej,wj; scanf("%d%d%d",&sj,&ej,&wj); if(sj<=ej && ej<=m && sj>0) { njob[cnt].s=sj; njob[cnt].f=ej; njob[cnt++].w=wj; } } sort(njob+1,njob+cnt,cmp); cal_p(cnt); memset(opt,0,sizeof(opt)); for(int i=1;i<cnt;i++) { opt[i]=max(opt[i-1],opt[p[i]]+njob[i].w); } printf("%d\n",opt[cnt-1]); } return 0; }