Hdu 6240 01分数规划
2017-11-14 18:07
288 查看
这个是CCPC哈尔滨的K题,当时听到隔壁THU卡题少女队说是01分数规划,没学过就弃了。后来发现这玩意挺傻逼的,今天掏出来BB了一顿很快就AC了。
题意: 从一堆[si,ti]的区间中选一部分完全覆盖[1, T], 每个区间有两个权值ai bi, 要求选用的区间的 ∑ai∑bi 的最小值。
做法: 先参考一下fjzzq大佬的文章https://www.cnblogs.com/zzqsblog/p/5450361.html , 发现01分数规划就是二分答案之后把分母乘上去,使得 ∑ai−bi∗mid 为正(负), 这个只要把 ai−bi∗mid 作为新的权值从大往小贪一下即可。然后在这个题里面,二分答案之后,显然正的部分全部要取完,这样就变成了如何用最少的代价覆盖剩下的区间,这个我把线段按左端点排序之后用bit维护dp就做完了。这样复杂度有两个log, 但是考虑到时限给了10s, 还是很轻松就AC了, 耗时2652ms。
代码:
题意: 从一堆[si,ti]的区间中选一部分完全覆盖[1, T], 每个区间有两个权值ai bi, 要求选用的区间的 ∑ai∑bi 的最小值。
做法: 先参考一下fjzzq大佬的文章https://www.cnblogs.com/zzqsblog/p/5450361.html , 发现01分数规划就是二分答案之后把分母乘上去,使得 ∑ai−bi∗mid 为正(负), 这个只要把 ai−bi∗mid 作为新的权值从大往小贪一下即可。然后在这个题里面,二分答案之后,显然正的部分全部要取完,这样就变成了如何用最少的代价覆盖剩下的区间,这个我把线段按左端点排序之后用bit维护dp就做完了。这样复杂度有两个log, 但是考虑到时限给了10s, 还是很轻松就AC了, 耗时2652ms。
代码:
#include <bits/stdc++.h> using namespace std; const int maxn=100007; int n, t; struct node { int s, t, a, b; bool tag; }rec[maxn]; bool cmp(node a, node b){ if(a.s==b.s)return a.t<b.t; return a.s<b.s; } bool vis[maxn]; double c[maxn]; int lowbit(int x){ return x&(-x); } void update(int x, double num){ while(x){ c[x]=min(c[x], num); x-=lowbit(x); } } double query(int x){ if(x==0)return 0; double ans=1e9; while(x<=t){ ans=min(ans, c[x]); x+=lowbit(x); } return ans; } bool check(double mid){ double sum=0; int r=0; for(int i=1;i<=t;i++){ c[i]=1e9; } for(int i=1;i<=n;i++){ if(rec[i].b*mid-rec[i].a>0){ sum+=rec[i].b*mid-rec[i].a; rec[i].tag=true; if(rec[i].s-1<=r){ r=max(r, rec[i].t); } } else rec[i].tag=false; } if(r==t)return true; update(r, 0); for(int i=1;i<=n;i++){ if(!rec[i].tag){ double from=query(rec[i].s-1); update(rec[i].t, from+rec[i].a-rec[i].b*mid); } else { double from=query(rec[i].s-1); update(rec[i].t, from); } } return sum>=query(t); } int main(){ int T; scanf("%d", &T); while(T--){ scanf("%d%d", &n, &t); for(int i=1;i<=n;i++){ scanf("%d%d%d%d", &rec[i].s, &rec[i].t, &rec[i].a, &rec[i].b); } sort(rec+1, rec+1+n, cmp); double l=0, r=1001; int tim=30; for(int i=1;i<=tim;i++){ double mid=(l+r)/2; if(check(mid))r=mid; else l=mid; } printf("%.3f\n", l); } }
相关文章推荐
- HDU 2676 Network Wars 01分数规划,最小割 难度:4
- 01分数规划入门 poj 2976, 2728, 3621
- hdu 6070 Dirt Ratio(分数规划)
- bzoj 4753: [Jsoi2016]最佳团体【01分数规划+二分+树上背包】
- poj2728 Desert King 【最优比例生成树 01分数规划】
- bzoj1486 [HNOI2009]最小圈 【最小比例环 01分数规划】
- poj3155 Hard Life 【最大密度图 01分数规划】
- 51 nod oj 1257 背包问题 V3【01分数规划】
- BZOJ1758: [Wc2010]重建计划(01分数规划+点分治+单调队列)
- bzoj 1690: [Usaco2007 Dec]奶牛的旅行(01分数规划--最优比率环)
- Codeforces 489E Hiking(普通01分数规划加DP)
- POJ 3757 Simple Distributed storage system 01分数规划
- poj2976 01分数规划
- POJ 2976 Dropping tests(01分数规划)
- 01分数规划模板
- zoj 2676 Network Wars(01分数规划+最小割)
- POJ 2976 Dropping tests [01分数规划]
- poj 2728 最优比例生成树(01分数规划)模板
- 【BZOJ 3316】JC loves Mkk 01分数规划+单调队列
- [Algorithm]01分数规划——Update:2012年7月27日