看了别人的题解。须要用到匈牙利算法的强连通算法

#include<cstdio>
#include<algorithm>
#include<vector>
#pragma comment(linker, "/STACK:1024000000,1024000000")
using namespace std;
const int MAXN = 1005;
int n, m;
int mb[MAXN], ma[MAXN];
bool vis[MAXN], gl[MAXN][MAXN];
vector<int> eg[MAXN];
vector<int> mmp[MAXN], res;
int dfs(int a)
{
for (int i = 0; i< eg[a].size(); ++i)
{
int v = eg[a][i];
if (!vis[v])
{
vis[v] = 1;
if (!mb[v] || dfs(mb[v]))
{
mb[v] = a;
ma[a] = v;
return 1;
}
}
}
return 0;
}
int hungary(int a)
{
int cnt = 0;
memset(mb, 0, sizeof mb);
for (int i = 1; i<= a; ++i)
{
memset(vis, 0, sizeof vis);
cnt += dfs(i);
}
return cnt;
}
int dfn[MAXN], low[MAXN], zu, belong[MAXN];
int nc;
int stk[MAXN], top, isinstk[MAXN];
void tarjan(int u)
{
dfn[u] = low[u] = nc++;
stk[top++] = u;
isinstk[u] = 1;
for (int i = 0; i< mmp[u].size(); ++i)
{
int v = mmp[u][i];
if (dfn[v] == -1)
{
tarjan(v);
low[u] = min(low[u], low[v]);
}
else if (isinstk[v] && low[u] > dfn[v])
{
low[u] = dfn[v];
}
}
if (dfn[u] == low[u])
{
int v;
do
{
v = stk[--top];
isinstk[v] = 0;
belong[v] = zu;
}while( v != u);
zu++;
}
}
int main()
{
#ifndef ONLINE_JUDGE
freopen("in.txt", "r", stdin);
#endif
int t;
scanf("%d", &t);
for (int o = 1; o<= t; ++o)
{
printf("Case #%d:\n", o);
scanf("%d%d", &n, &m);
for (int i = 1; i<= n; ++i)
{
int k, a;
scanf("%d", &k);
eg[i].clear();
while (k--)
{
scanf("%d", &a);
eg[i].push_back(a);
}
}
int cna = hungary(n);
cna = n+m-cna;
for (int i=n+1; i<= cna; ++i)
{
eg[i].clear();
for (int j = 1; j<= cna; ++j)
{
eg[i].push_back(j);
}
}
for (int i=m+1; i<= cna; ++i)
{
for (int j = 1; j<= n; ++j)
{
eg[j].push_back(i);
}
}
int nmc = hungary(cna);
for (int i = 1; i<= cna; ++i) mmp[i].clear();
for (int i = 1; i<= cna; ++i)
{
int a = mb[i];
for (int j = 0; j< eg[a].size(); ++j)
{
int v = eg[a][j];
if (v == i) continue;
mmp[i].push_back(v);
}
}
nc = 1;
memset(dfn, -1, sizeof dfn);
memset(low, -1, sizeof low);
top = 0;
zu = 0;
for (int i = 1; i<= cna; ++i)
{
if (dfn[i] == -1)
tarjan(i);
}
memset(gl, 0, sizeof gl);
for (int i = 1; i<= cna; ++i)
{
for (int j = 0; j< eg[i].size(); ++j)
{
gl[i][eg[i][j]] = 1;
}
}
for (int i = 1; i<= n; ++i)
{
res.clear();
for (int j = 1; j<= m; ++j)
{
if (gl[i][j] && belong[j] == belong[ma[i]])
res.push_back(j);
}
int sz = res.size();
printf("%d", sz);
for (int j = 0; j< sz; ++j)
{
printf(" %d", res[j]);
}
puts("");
}
}
return 0;
}

hdu 4685 Prince and Princess(匈牙利算法 连通分量)的更多相关文章

  1. HDU 4685 Prince and Princess 二分图匹配+tarjan

    Prince and Princess 题目连接: http://acm.hdu.edu.cn/showproblem.php?pid=4685 Description There are n pri ...

  2. HDU 4685 Prince and Princess (2013多校8 1010题 二分匹配+强连通)

    Prince and Princess Time Limit: 6000/3000 MS (Java/Others)    Memory Limit: 65535/32768 K (Java/Othe ...

  3. HDU 4685 Prince and Princess(二分图+强连通分量)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4685 题意:给出n个王子和m个公主.每个王子有一些自己喜欢的公主可以匹配.设最大匹配为M.那么对于每个 ...

  4. HDU 4685 Prince and Princess(二分匹配+强联通分量)

    题意:婚配问题,但是题目并不要求输出最大匹配值,而是让我们输出,一个王子可以与哪些王妃婚配而不影响最大匹配值. 解决办法:先求一次最大匹配,如果有两个已经匹配的王妃,喜欢她们两个的有两个或者以上相同的 ...

  5. HDU 4685 Prince and Princess

    强连通分量,看大神的题解才会写的.... http://www.cnblogs.com/kuangbin/p/3261157.html 数据量有点大,第一次Submit 2995ms过的,时限3000 ...

  6. hdu 2063 给男女匹配 (匈牙利算法)

    来源:http://acm.hdu.edu.cn/showproblem.php?pid=2063 题意: 有k个组合a,b组合,代表a愿意与b坐过山车,共m个女生 n个男生,问有多少个满意的匹配 题 ...

  7. HDU 2063 过山车 (匈牙利算法)

    题目链接:HDU 2063 Problem Description RPG girls今天和大家一起去游乐场玩,终于可以坐上梦寐以求的过山车了.可是,过山车的每一排只有两个座位,而且还有条不成文的规矩 ...

  8. hdu 1013 过山车 匈牙利算法(代码+详细注释)

    过山车 Time Limit: 1000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submis ...

  9. hdu 2063 过山车(匈牙利算法模板)

    http://acm.hdu.edu.cn/showproblem.php?pid=2063 过山车 Time Limit: 1000/1000 MS (Java/Others)    Memory ...

随机推荐

  1. PHP学习之-1.3 echo语句

    echo语句 echo语句是PHP输出语句,可以把字符串输出(字符串用双引号扩起来). 如下代码 <?php echo "Hello World!"; ?> 注意ech ...

  2. UVA 10911 Forming Quiz Teams(dp + 集合最优配对问题)

    4th IIUC Inter-University Programming Contest, 2005 G Forming Quiz Teams Input: standard input Outpu ...

  3. 14.10.5 Reclaiming Disk Space with TRUNCATE TABLE 回收空间使用TRUNCATE TABLE

    14.10.5 Reclaiming Disk Space with TRUNCATE TABLE 回收空间使用TRUNCATE TABLE 回收操作系统磁盘空间当truncate 一个InnoDB ...

  4. JavaScript进阶(三) 值传递和引用传递

    从C语言开始 有时候讲一些细节或是底层的东西,我喜欢用C语言来讲,因为用C更方便来描述内存里面的东西.先举一个例子,swap函数,相信有一些编程经验的人都见识过,声明如下,函数体我就不写了,各位脑补一 ...

  5. Problem D: Flip Five

    大致题意:3 * 3的黑白格,在翻转的时候会本身和四周的都翻转,问最小翻转几次变成全部是白色解题思路:把3 * 3 = 9 个格子进行全排列,然后穷举然后找翻转的最小次数 #include <i ...

  6. 利用PS滤镜及图层叠加制作水墨荷花

    水墨荷花制作思路并不复杂:把图片转为黑白,用滤镜等增加水墨纹理即可.不过在处理的时候还有很多细节需要处理,如图片的背景,水墨纹理控制范围等,这些需要自己慢慢摸索. 原图 最终效果 1.打开素材图片,把 ...

  7. Swift - 设置程序的应用图标和启动界面

    一个应用,无论发布到App Store,还是安装到用户的屏幕上,都需要一个标志性的图标.同时,在应用启动时也要有个启动画面,否则启动时将会是纯黑的屏幕. 1,在项目的“General”选项卡下的“Ap ...

  8. Delphi的TService的輸入桌面切換(服务程序)(windows登录界面如何截图)(使用了OpenDesktop和GetThreadDesktop等API)

    dfm: object CopyDeskService: TCopyDeskService  OldCreateOrder = False  OnCreate = ServiceCreate  OnD ...

  9. cct信息安全

    基本信息 全国计算机等级考试三级教程——信息安全技术(2016年版) 作    者:教育部考试中心 编 出 版 社:高等教育出版社 出版时间:2015-12-1 ISBN:9787040443035 ...

  10. Swift - 页控件(UIPageControl)的用法

    使用页控件可以用来展示多个桌面.比如很多应用第一次登陆时,会在开始页面使用页控件来介绍功能,通过左右滑动来切换页. 通常我们使用UIPageControl和UIScrollView相互结合来实现多页切 ...