HDU 1074 Doing Homework【状态压缩DP】
2016-04-04 11:10
387 查看
题目链接:
http://acm.hdu.edu.cn/showproblem.php?pid=1074题意:
给定作业截止时间和完成作业所需时间,比截止时间晚一天扣一分,问如何安排作业的顺序使得最终扣分最少?分析:
最多只有15节课,可以将完成作业的情况进行状态压缩,用二进制表示,枚举出状态,进行dp。然后注意输入的时候本身就是字典序最小的,倒着来一遍,先不写后面的作业,这样最终得到的答案就是按字典序小的排列的了。
dp最初忘记1<<maxn,悲哀的TLE了两发。。
代码:
#include<iostream> #include<cstdio> #include<cstring> #include<cmath> using namespace std; #define sa(a) scanf("%d", &a) #define sal(a) scanf("%I64d", &a) const int maxn = 15 + 5, INF = 0x3f3f3f3f; struct hwk{char s[105]; int d;int c;}; hwk p[maxn]; struct DP{int day; int pre; int v;}; DP dp[1<<maxn]; int n; void print(int st) { if(!st) return; print(dp[st].pre); int now = dp[st].pre^st; int res; for(int i = 0; i < n; i++){ if(now >> i & 1) {res = i;break;} } printf("%s\n", p[res].s); } int main (void) { int T;sa(T); while(T--){ sa(n); for(int i = 0; i < (1<<n); i++){ dp[i].day = 0; dp[i].pre = 0; dp[i].v = INF; } dp[0].v = 0; for(int i = 0; i < n; i++){ scanf("%s", p[i].s); sa(p[i].d); sa(p[i].c); } int en = 1 << n; for(int i = 1; i < en; i++){ for(int j = n - 1; j >= 0; j--){ if(i>>j & 1){ int be = i - (1 << j); int tmp = dp[be].day + p[j].c - p[j].d; if(tmp < 0) tmp = 0; if(tmp + dp[be].v < dp[i].v){ dp[i].v = tmp + dp[be].v; dp[i].pre = be; dp[i].day = dp[be].day + p[j].c; } } } } printf("%d\n", dp[en - 1].v); print(en -1); } return 0; }
相关文章推荐
- #号称5秒1000个包的超快速多渠道打包方式
- HDU 1074 Doing Homework【状态压缩DP】
- 使用extern "C"改善显式调用dll
- 聊聊Android应用实现跨进程调用
- SVN服务器&客户端的搭建和使用
- 关于新手语言一些想法(本人也是小白)
- n阶蛇形矩阵
- 用String类和Integer等基本数据类型包装类进行实例化对象时的工作原理
- 关于eclipse或Android studio中adb连接上不了手机的解决方法
- 关于KD树(未完)
- 杭电2602Bone Collector(01背包)
- eclipse web开发插件安装
- python三目表达式
- C++实现IP地址类
- CodeForces 652D Nested Segments (树状数组)
- Gson完全解析
- 定时器,监听器
- 引入ping++的server SDK,thinkphp报错:unexpected 符号“,”
- JAVA 对象引用,以及对象赋值
- Struts2的一点人生经验