HDU 3081 Marriage Match II

pid=3081" target="_blank" style="">题目链接

题意:n个女孩n个男孩,每一个女孩能够和一些男孩配对。然后有些女孩是朋友。满足这个朋友圈里面的人,假设有一个能和某个男孩配对,其它就都能够,然后每轮要求每一个女孩匹配到一个男孩。且每轮匹配到的都不同,问最多能匹配几轮

思路:二分轮数k,然后建图为,源点连向女孩,男孩连向汇点容量都为k,然后女孩和男孩之间连边为。有关系的连边容量1,这样一个匹配相应一条边。且不会反复,每次推断最大流是否等于n * k就可以

代码:

#include <cstdio>
#include <cstring>
#include <queue>
#include <algorithm>
using namespace std; const int MAXNODE = 205;
const int MAXEDGE = 100005; typedef int Type;
const Type INF = 0x3f3f3f3f; struct Edge {
int u, v;
Type cap, flow;
Edge() {}
Edge(int u, int v, Type cap, Type flow) {
this->u = u;
this->v = v;
this->cap = cap;
this->flow = flow;
}
}; struct Dinic {
int n, m, s, t;
Edge edges[MAXEDGE];
int first[MAXNODE];
int next[MAXEDGE];
bool vis[MAXNODE];
Type d[MAXNODE];
int cur[MAXNODE];
vector<int> cut; void init(int n) {
this->n = n;
memset(first, -1, sizeof(first));
m = 0;
}
void add_Edge(int u, int v, Type cap) {
edges[m] = Edge(u, v, cap, 0);
next[m] = first[u];
first[u] = m++;
edges[m] = Edge(v, u, 0, 0);
next[m] = first[v];
first[v] = m++;
} bool bfs() {
memset(vis, false, sizeof(vis));
queue<int> Q;
Q.push(s);
d[s] = 0;
vis[s] = true;
while (!Q.empty()) {
int u = Q.front(); Q.pop();
for (int i = first[u]; i != -1; i = next[i]) {
Edge& e = edges[i];
if (!vis[e.v] && e.cap > e.flow) {
vis[e.v] = true;
d[e.v] = d[u] + 1;
Q.push(e.v);
}
}
}
return vis[t];
} Type dfs(int u, Type a) {
if (u == t || a == 0) return a;
Type flow = 0, f;
for (int &i = cur[u]; i != -1; i = next[i]) {
Edge& e = edges[i];
if (d[u] + 1 == d[e.v] && (f = dfs(e.v, min(a, e.cap - e.flow))) > 0) {
e.flow += f;
edges[i^1].flow -= f;
flow += f;
a -= f;
if (a == 0) break;
}
}
return flow;
} Type Maxflow(int s, int t) {
this->s = s; this->t = t;
Type flow = 0;
while (bfs()) {
for (int i = 0; i < n; i++)
cur[i] = first[i];
flow += dfs(s, INF);
}
return flow;
} void MinCut() {
cut.clear();
for (int i = 0; i < m; i += 2) {
if (vis[edges[i].u] && !vis[edges[i].v])
cut.push_back(i);
}
}
} gao; const int N = 105; int t, n, m, f, g[N][N], parent[N]; int find(int x) {
return x == parent[x] ? x : parent[x] = find(parent[x]);
} bool judge(int k) {
int s = 0, t = n * 2 + 1;
gao.init(t + 1);
for (int i = 1; i <= n; i++) {
gao.add_Edge(s, i, k);
gao.add_Edge(i + n, t, k);
for (int j = 1; j <= n; j++)
if (g[i][j]) gao.add_Edge(i, j + n, 1);
}
return gao.Maxflow(s, t) == n * k;
} int main() {
scanf("%d", &t);
while (t--) {
scanf("%d%d%d", &n, &m, &f);
memset(g, 0, sizeof(g));
for (int i = 1; i <= n; i++) parent[i] = i;
int u, v;
while (m--) {
scanf("%d%d", &u, &v);
g[u][v] = 1;
}
while (f--) {
scanf("%d%d", &u, &v);
int pa = find(u);
int pb = find(v);
if (pa != pb) parent[pa] = pb;
}
for (int i = 1; i <= n; i++)
for (int j = 1; j <= n; j++) {
if (find(i) == find(j)) {
for (int k = 1; k <= n; k++)
g[i][k] |= g[j][k];
}
}
int l = 1, r = n + 1;
while (l < r) {
int mid = (l + r) / 2;
if (judge(mid)) l = mid + 1;
else r = mid;
}
printf("%d\n", l - 1);
}
return 0;
}

版权声明:本文博客原创文章,博客,未经同意,不得转载。

HDU 3081 Marriage Match II(二分法+最大流量)的更多相关文章

  1. HDU 3081 Marriage Match II (网络流,最大流,二分,并查集)

    HDU 3081 Marriage Match II (网络流,最大流,二分,并查集) Description Presumably, you all have known the question ...

  2. HDU 3081 Marriage Match II (二分图,并查集)

    HDU 3081 Marriage Match II (二分图,并查集) Description Presumably, you all have known the question of stab ...

  3. HDU 3081 Marriage Match II 二分 + 网络流

    Marriage Match II 题意:有n个男生,n个女生,现在有 f 条男生女生是朋友的关系, 现在有 m 条女生女生是朋友的关系, 朋友的朋友是朋友,现在进行 k 轮游戏,每轮游戏都要男生和女 ...

  4. HDU 3081 Marriage Match II 最大流OR二分匹配

    Marriage Match IIHDU - 3081 题目大意:每个女孩子可以和没有与她或者是她的朋友有过争吵的男孩子交男朋友,现在玩一个游戏,每一轮每个女孩子都要交一个新的男朋友,问最多可以玩多少 ...

  5. HDU - 3081 Marriage Match II 【二分匹配】

    题目链接 http://acm.hdu.edu.cn/showproblem.php?pid=3081 题意 有n对男女 女生去选男朋友 如果女生从来没和那个男生吵架 那么那个男生就可以当她男朋友 女 ...

  6. HDU 3081 Marriage Match II

    二分图的最大匹配+并查集 每次匹配完之后,删除当前匹配到的边. #include<cstdio> #include<cstring> #include<cmath> ...

  7. HDU 3081 Marriage Match II (二分+并查集+最大流)

    题意:N个boy和N个girl,每个女孩可以和与自己交友集合中的男生配对子;如果两个女孩是朋友,则她们可以和对方交友集合中的男生配对子;如果女生a和女生b是朋友,b和c是朋友,则a和c也是朋友.每一轮 ...

  8. HDU 3081 Marriage Match II (二分+网络流+并查集)

    注意 这题需要注意的有几点. 首先板子要快,尽量使用带当前弧优化的dinic,这样跑起来不会超时. 使用弧优化的时候,如果源点设置成0,记得将cur数组从0开始更新,因为有的板子并不是. 其次这题是多 ...

  9. hdu 3081 hdu 3277 hdu 3416 Marriage Match II III IV //灵活运用最大流量

    3081 意甲冠军: n女生选择不吵架,他甚至男孩边(他的朋友也算.并为您收集过程).2二分图,一些副作用,有几个追求完美搭配(每场比赛没有重复的每一个点的比赛) 后.每次增广一单位,(一次完美匹配) ...

随机推荐

  1. php laravel 帧 该文件上传

    好,我承认我的忠告. 今天laravel框架编写一个文件上传部分.总能找到不正确的路径.但是,终于攻克. 以下我分享一下自己的学习体会吧. client <form method="P ...

  2. SharePoint 2010 新列表模板列表

    SharePoint 2010 新列表模板列表 项目描述叙事 发展环境创造了良好的名单为模板.然后使用列表模板将其复制到生产环境. 脚步 1. 打开"列表设置",找到"将 ...

  3. 小米2S twrp 中文,支持双系统

    更新日志: 更新日志: 汉化了要使用的功能 修改语言选择方式,修改为下拉方式 TDB(TrueDualBoot) 功能完美实现 **adb**功能,完美实现,无需特别操作(比CWM强大) 修改双系统切 ...

  4. Java Web整合开发(80) -- EJB & WebService

    1. jdk-6u18-windows-i586-p.execlasspath: .;%JAVA_HOME%lib/tools.jar;%JAVA_HOME%lib/dt.jar;%JAVA_HOME ...

  5. js在以div添加滚动条

    给予div另外,当我们必须定义高度和宽度的滚动条,使滚动条是有效,增加样式:overflow:auto; 版权声明:本文博主原创文章.博客,未经同意不得转载.

  6. sql function递归

    alter function Fn_GetUserGroupRelation ( @DHsItemID int ) returns nvarchar(1024) begin declare @Col_ ...

  7. 【Linux探索之旅】第一部分第六课:Linux如何安装在虚拟机中

    内容简介 1.第一部分第六课:Linux如何安装在虚拟机中 2.第二部分第一课预告:终端Terminal,好戏上场 Linux如何安装在虚拟机中 虽然我们带大家一起在电脑的硬盘上安装了Ubuntu这个 ...

  8. MongoDB学习笔记-基础概念

    mongodb中基本的概念 文档.集合.数据库 与关系数据库的概念对比更容易理解

  9. MATLAB描绘极坐标图像——polar

    polar可用于描绘极坐标图像. 最简单而经常使用的命令格式:POLAR(THETA, RHO)  当中,THETA是用弧度制表示的角度,RHO是相应的半径. 例: a=-2*pi:.001:2*pi ...

  10. Android复制iPhone日期和时间选择器

    看效果图 watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvbGluZ2xvbmd4aW4yNA==/font/5a6L5L2T/fontsize/400/fi ...