hdu2883 kebab
2016-02-24 23:07
531 查看
有n个人分别在s[i]时间到烧烤摊去,然后t[i]离开,点了need[i]串烤串,每串需要cost[i]的时间烤,烧烤摊有个烤箱,但是一次最多烤m串。由于题目中说过,每个烤串是可以拆开来烤,也就是说假如一个烤串需要f分钟,那么我们可以将其拆成f分,每分钟烤其中的m分,这样的话花的时间就是f/m,如果其余数不为0的话就+1。这样一来,我们可以将所有的烤串全部拆分成最小的份数。
这样的话超级源点就就和每个客人建边,容量为need[i]*cost[i]。后面我们就需要求出时间区间了(因为如果按照每分钟当作一个点的话,点太多,会超时的)。把每个区间当作一个点,如果某个区间是某个人到与离开的时间之间的话,就可以建边,容量为inf,然后每个区间与超级汇点就是建立一条容量为区间范围*m的边。
附上大神的讲解:http://blog.csdn.net/u013480600/article/details/38984057
这样的话超级源点就就和每个客人建边,容量为need[i]*cost[i]。后面我们就需要求出时间区间了(因为如果按照每分钟当作一个点的话,点太多,会超时的)。把每个区间当作一个点,如果某个区间是某个人到与离开的时间之间的话,就可以建边,容量为inf,然后每个区间与超级汇点就是建立一条容量为区间范围*m的边。
附上大神的讲解:http://blog.csdn.net/u013480600/article/details/38984057
/***************************************** Author :Crazy_AC(JamesQi) Time :2016 File Name : *****************************************/ // #pragma comment(linker, "/STACK:1024000000,1024000000") #include <iostream> #include <algorithm> #include <iomanip> #include <sstream> #include <string> #include <stack> #include <queue> #include <deque> #include <vector> #include <map> #include <set> #include <cstdio> #include <cstring> #include <cmath> #include <cstdlib> #include <climits> using namespace std; #define MEM(x,y) memset(x, y,sizeof x) #define pk push_back typedef long long LL; typedef unsigned long long ULL; typedef pair<int,int> ii; typedef pair<ii,int> iii; const double eps = 1e-10; const int inf = 1 << 30; const int INF = 0x3f3f3f3f; const int MOD = 1e9 + 7; const int maxn = 1e5 + 10; struct Edge{ int from, to, cap, flow; Edge(){} Edge(int from,int to,int cap,int flow):from(from),to(to),cap(cap),flow(flow){} }; struct ISAP{ int p[maxn], num[maxn], cur[maxn], d[maxn]; int s, t, n, m; bool vis[maxn]; vector<int> G[maxn]; vector<Edge> edges; void init(int n) { this->n = n; for (int i = 0;i <= n;++i) { G[i].clear(); d[i] = INF; } edges.clear(); } void addedge(int from,int to,int cap) { edges.push_back(Edge(from, to, cap, 0)); edges.push_back(Edge(to, from, 0, 0)); m = (int)edges.size(); G[from].push_back(m - 2); G[to].push_back(m - 1); } bool bfs() { memset(vis, false,sizeof vis); queue<int> que; d[t] = 0; vis[t] = true; que.push(t); while(!que.empty()) { int u = que.front(); que.pop(); for (int i = 0;i < G[u].size();++i) { Edge& e = edges[G[u][i]^1]; if (e.cap > e.flow && !vis[e.from]) { vis[e.from] = true; d[e.from] = d[u] + 1; que.push(e.from); } } } return vis[s]; } int Augment() { int u = t, flow = INF; while(u != s) { Edge& e = edges[p[u]]; flow = min(flow, e.cap - e.flow); u = edges[p[u]].from; } u = t; while(u != s) { edges[p[u]].flow += flow; edges[p[u]^1].flow -= flow; u = edges[p[u]].from; } return flow; } int MaxFlow(int s,int t) { this->s = s,this->t = t; int ret = 0; bfs(); if (d[s] >= n) return 0; memset(num, 0,sizeof num); memset(cur, 0,sizeof cur); for (int i = 0;i < n;++i) { if (d[i] < INF) num[d[i]]++; } int u = s; while(d[s] < n) { if (u == t) { ret += Augment(); u = s; } bool ok = false; for (int i = cur[u];i < G[u].size();++i) { Edge& e = edges[G[u][i]]; if (e.cap > e.flow && d[u] == d[e.to] + 1) { ok = true; p[e.to] = G[u][i]; cur[u] = i; u = e.to; break; } } if (!ok) { int Min = n - 1; for (int i = 0;i < G[u].size();++i) { Edge& e = edges[G[u][i]]; if (e.cap > e.flow) Min = min(Min, d[e.to]); } if (--num[d[u]] == 0) break; num[d[u] = Min + 1]++; cur[u] = 0; if (u != s) u = edges[p[u]].from; } } return ret; } }isap; int n, m; int st[maxn], ed[maxn], need[maxn], cost[maxn]; int tmp[maxn]; int main() { // freopen("in.txt","r",stdin); // freopen("out.txt","w",stdout); while(scanf("%d%d",&n,&m) != EOF) { int j = 0; int sum = 0; for (int i = 1;i <= n;++i) { scanf("%d%d%d%d",&st[i],&need[i],&ed[i],&cost[i]); sum += need[i]*cost[i]; tmp[++j] = st[i]; tmp[++j] = ed[i]; } sort(tmp + 1,tmp + 1 + j); int cnt = unique(tmp + 1,tmp + 1 + j) - tmp - 1; int s = 0, t = n + cnt + 1; isap.init(t); for (int i = 1;i <= n;++i) { isap.addedge(s, i, cost[i]*need[i]); for (j = 2;j <= cnt;++j) { if (st[i] <= tmp[j-1] && ed[i] >= tmp[j]) { isap.addedge(i, j - 1 + n, INF); } } } for (int i = 2;i <= cnt;++i) isap.addedge(i - 1 + n, t, (tmp[i] - tmp[i-1])*m); int ans = isap.MaxFlow(s, t); if (ans == sum) puts("Yes"); else puts("No"); } return 0; }
相关文章推荐
- Scrapinghub执行spider抓取并显示图片
- 封装使用ViewHolder模式的Adapter组件,及用其快速实现聊天界面
- leetcode 318. Maximum Product of Word Lengths
- 17229 Lry,你除了2还是2
- sublime 安装 php xdebug
- 服务器IBM 3650M3 内存插法
- Mina(三)
- swift基本语法(总结提炼版)之007 swift之数组
- 【MFC-9】VS2010/MFC基于对话框的SQlite3数据库编程
- Java堆外内存之突破JVM枷锁
- Rigidbody SweepTest测试
- 毕业设计第九天
- SUSE Linux上安装IPython/Jupyter
- HTML+CSS慕课网学习总结(三)
- C#Winform读取txt文件
- Python操作Mysql实例代码
- #Android学习#启动、绑定及跨应用启动Service
- leetcode Partition List二分链表问题
- iOS网络2——NSURLSession使用详解
- [OJ] Wildcard Matching (Hard)