hdu 3189(网络流+二分枚举)
| Time Limit: 1000MS | Memory Limit: 65536K | |
| Total Submissions: 6422 | Accepted: 2202 |
Description
FJ would like to rearrange the cows such that the cows are as
equally happy as possible, even if that means all the cows hate their
assigned barn.
Each cow gives FJ the order in which she prefers the barns. A cow's
happiness with a particular assignment is her ranking of her barn. Your
job is to find an assignment of cows to barns such that no barn's
capacity is exceeded and the size of the range (i.e., one more than the
positive difference between the the highest-ranked barn chosen and that
lowest-ranked barn chosen) of barn rankings the cows give their assigned
barns is as small as possible.
Input
Lines 2..N+1: Each line contains B space-separated integers which
are exactly 1..B sorted into some order. The first integer on line i+1
is the number of the cow i's top-choice barn, the second integer on that
line is the number of the i'th cow's second-choice barn, and so on.
Line N+2: B space-separated integers, respectively the capacity of
the first barn, then the capacity of the second, and so on. The sum of
these numbers is guaranteed to be at least N.
Output
Sample Input
6 4
1 2 3 4
2 3 1 4
4 2 3 1
3 1 2 4
1 3 4 2
1 4 2 3
2 1 3 2
Sample Output
2
Hint
Each cow can be assigned to her first or second choice: barn 1 gets
cows 1 and 5, barn 2 gets cow 2, barn 3 gets cow 4, and barn 4 gets cows
3 and 6.
#include <stdio.h>
#include <algorithm>
#include <queue>
#include <string.h>
#include <math.h>
#include <iostream>
#include <math.h>
using namespace std;
const int N = ;
const int INF = ;
struct Edge{
int v,next;
int w;
}edge[N*N];
struct Cow{
int love[];
}cow[N];
int head[N];
int level[N];
int graph[N][N],dis[N][N],cap[N];
int tot;
void init(){
memset(head,-,sizeof(head));
tot=;
}
void addEdge(int u,int v,int w,int &k){
edge[k].v = v,edge[k].w=w,edge[k].next=head[u],head[u]=k++;
edge[k].v = u,edge[k].w=,edge[k].next=head[v],head[v]=k++;
}
int BFS(int src,int des){
queue<int >q;
memset(level,,sizeof(level));
level[src]=;
q.push(src);
while(!q.empty()){
int u = q.front();
q.pop();
if(u==des) return ;
for(int k = head[u];k!=-;k=edge[k].next){
int v = edge[k].v;
int w = edge[k].w;
if(level[v]==&&w!=){
level[v]=level[u]+;
q.push(v);
}
}
}
return -;
}
int dfs(int u,int des,int increaseRoad){
if(u==des) return increaseRoad;
int ret=;
for(int k=head[u];k!=-;k=edge[k].next){
int v = edge[k].v;
int w = edge[k].w;
if(level[v]==level[u]+&&w!=){
int MIN = min(increaseRoad-ret,w);
w = dfs(v,des,MIN);
if(w>){
edge[k].w -=w;
edge[k^].w+=w;
ret+=w;
if(ret==increaseRoad) return ret;
}else level[v] = -;
}
}
return ret;
}
int Dinic(int src,int des){
int ans = ;
while(BFS(src,des)!=-) ans+=dfs(src,des,INF);
return ans;
}
int n,b,src,des;
int build(int t,int mid){
init();
for(int i=;i<=b;i++){
addEdge(src,i,cap[i],tot);
}
for(int i=;i<=n;i++){
addEdge(i+b,des,,tot);
}
for(int i=t;i<=t+mid-&&i<=b;i++){
for(int j=;j<=n;j++){
addEdge(cow[j].love[i],j+b,,tot);
}
}
return Dinic(src,des);
}
int main(){
scanf("%d%d",&n,&b);
src = ,des = n+b+;
for(int i=;i<=n;i++){
for(int j=;j<=b;j++){
scanf("%d",&cow[i].love[j]);
}
}
for(int i=;i<=b;i++) scanf("%d",&cap[i]);
int l =,r = b;
int ans = b;
while(l<=r){
int mid = (l+r)>>; ///差值
bool flag = false;
for(int i=;i<=b;i++){ ///枚举最小值
if(build(i,mid)==n) {
flag = ;
break;
}
}
if(flag) {
ans = mid;
r = mid-;
}else l = mid+;
}
printf("%d\n",ans);
}
hdu 3189(网络流+二分枚举)的更多相关文章
- 无题II hdu 2236(二分枚举区间)
分析:只需要用二分找一个区间,然后不断枚举这个区间是否可以达到最大匹配,一直二分到答案为止. 代码: =============================================== ...
- hdu 5289 rmp+二分+枚举后界 or单调队列 ****
好题~~ 给你n个数和k,求有多少的区间使得区间内部任意两个数的差值小于k,输出符合要求的区间个数,枚举后界~~ 又是一种没见过的方法,太弱了/(ㄒoㄒ)/~~ #include <cstdio ...
- HDU 1669 Jamie's Contact Groups(多重匹配+二分枚举)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1669 题目大意: 给你各个人可以属于的组,把这些人分组,使这些组中人数最多的组人数最少,并输出这个人数 ...
- POJ 3189——Steady Cow Assignment——————【多重匹配、二分枚举区间长度】
Steady Cow Assignment Time Limit:1000MS Memory Limit:65536KB 64bit IO Format:%I64d & %I ...
- hdu 5248 序列变换(二分枚举)
Problem Description 给定序列A={A1,A2,...,An}, 要求改变序列A中的某些元素,形成一个严格单调的序列B(严格单调的定义为:Bi<Bi+,≤i<N). 我们 ...
- hdu 4430 二分+枚举
/* 二分+枚举 枚举k会超时,枚举r还要优化,有可能会超64 */ #include<stdio.h> #include<math.h> #define ll __int64 ...
- BFS+状态压缩DP+二分枚举+TSP
http://acm.hdu.edu.cn/showproblem.php?pid=3681 Prison Break Time Limit: 5000/2000 MS (Java/Others) ...
- FZU-2216 The Longest Straight (二分枚举)
题目大意:给n个0~m之间的数,如果是0,那么0可以变为任意的一个1~m之间的一个数.从中选出若干个数,使构成一个连续的序列.问能构成的最长序列的长度为多少? 题目分析:枚举连续序列的起点,二分枚举二 ...
- hdu 4768 Flyer 二分
思路:由于最多只有一个是奇数,所以二分枚举这个点,每次判断这个点的左边区间段所有点的和作为 二分的依据. 代码如下: #include<iostream> #include<cstd ...
随机推荐
- java 会话跟踪技术
1.session用来表示用户会话,session对象在服务端维护,一般tomcat设定session生命周期为30分钟,超时将失效,也可以主动设置无效: 2.cookie存放在客户端,可以分为内存c ...
- 【主席树】bzoj1112: [POI2008]砖块Klo
数据结构划一下水 Description N柱砖,希望有连续K柱的高度是一样的. 你可以选择以下两个动作 1:从某柱砖的顶端拿一块砖出来,丢掉不要了. 2:从仓库中拿出一块砖,放到另一柱.仓库无限大. ...
- python入门:CONTINUE 的作用 跳出本次循环后,重新开始循环
#!/usr/bin/env python # -*- coding:utf-8 -*- # CONTINUE 的作用 跳出本次循环后,重新开始循环 import time while True: ' ...
- CUB reduce errorinvalid configuration argument
解决CUB reduce errorinvalid configuration argument问题 在写TensorFlow代码时遇到报错 CUB reduce errorinvalid confi ...
- Python入门基础--字符编码与文件处理
字符编码 文本编辑器存取文件的原理 #1.打开编辑器就打开了启动了一个进程,是在内存中的,所以,用编辑器编写的内容也都是存放与内存中的,断电后数据丢失 #2.要想永久保存,需要点击保存按钮:编辑器把内 ...
- 牛客网暑期ACM多校训练营(第七场)A Minimum Cost Perfect Matching(找规律)
题意: 给定n, 求一个0~n-1的全排列p, 使得的和最小 分析: 打表发现最优解肯定是和为0的, 然后如果为2的幂就是直接反转即可, 不然的话就要分开从前面到后面逐步拆分, 具体思想模拟一下n = ...
- PAT Basic 1079
1079 延迟的回文数(20 分) 给定一个 k+1 位的正整数 N,写成 ak⋯a1a0 的形式,其中对所有 i 有 0≤ai<10 且 ak>0.N 被称 ...
- TypeError: cannot use a string pattern on a bytes-like object
一劳永逸解决:TypeError: cannot use a string pattern on a bytes-like object TypeError: cannot use a string ...
- vagrant 安装ubuntu12.04 64 bit
1 下载用于ubuntu 12.04 用于vagrant的镜像,虚拟机是virtualbox $ wget http://files.vagrantup.com/precise64.box jb@e3 ...
- JS实现——Base64编码解码,带16进制显示
在网上找了个JS实现的Base64编码转换,所以就想自己研究下,界面如下: 将代码以BASE64方式加密.解密 请输入要进行编码或解码的字符: 编码结果以ASCII码16进制显示 解码结果以ASCII ...