强连通分量,看大神的题解才会写的....

http://www.cnblogs.com/kuangbin/p/3261157.html

数据量有点大,第一次Submit 2995ms过的,时限3000ms,差一点就TLE了。

#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<vector>
using namespace std; const int maxn = + ;
int N, M;
vector<int>Cun[maxn];
vector<int>G[maxn];
vector<int>FG[maxn];
int nx, ny, Time, Block;
int g[maxn][maxn];
int cx[maxn], cy[maxn];
int mk[maxn];
int flag[maxn], dfn[maxn], Belong[maxn];
struct Point
{
int id, dfn;
} point[maxn]; int Scan()
{
int res = , ch, flag = ; if ((ch = getchar()) == '-') //判断正负
flag = ; else if (ch >= '' && ch <= '') //得到完整的数
res = ch - '';
while ((ch = getchar()) >= '' && ch <= '')
res = res * + ch - ''; return flag ? -res : res;
} bool cmp(const Point&a, const Point&b)
{
return a.dfn>b.dfn;
} int path(int u)
{
for (int v = ; v <= ny; v++)
{
if (g[u][v] && !mk[v])
{
mk[v] = ;
if (cy[v] == - || path(cy[v]))
{
cx[u] = v;
cy[v] = u;
return ;
}
}
}
return ;
} int MaxMatch()
{
int res = ;
memset(cx, -, sizeof(cx));
memset(cy, -, sizeof(cy));
for (int i = ; i <= nx; i++)
{
if (cx[i] == -)
{
memset(mk, , sizeof(mk));
res = res + path(i);
}
}
return res;
} void dfs(int now)
{
flag[now] = ;
for (int i = ; i<G[now].size(); i++)
if (!flag[G[now][i]])
dfs(G[now][i]);
Time++;
dfn[now] = Time;
} void Dfs(int now)
{
Belong[now] = Block;
for (int i = ; i<FG[now].size(); i++)
if (!Belong[FG[now][i]])
Dfs(FG[now][i]);
} int main()
{
int CA;
CA = Scan();
for (int er = ; er <= CA; er++){
N = Scan();
M = Scan();
memset(flag, , sizeof(flag));
memset(dfn, , sizeof(dfn));
memset(Belong, , sizeof(Belong));
Time = , Block = ;
for (int i = ; i<maxn; i++) G[i].clear();
for (int i = ; i<maxn; i++) Cun[i].clear();
for (int i = ; i<maxn; i++) FG[i].clear();
memset(g, , sizeof(g));
nx = N, ny = M; for (int i = ; i <= N; i++)
{
int ToT, To;
ToT = Scan();
while (ToT--)
{
To = Scan();
Cun[i].push_back(To);
g[i][To] = ;
}
sort(Cun[i].begin(), Cun[i].end());
}
int res = MaxMatch(); memset(g, , sizeof(g));
int A = M - res, B = N - res;//A表示虚拟王子数量,B表示虚拟妹子数量
nx = N + A, ny = M + B;
if (B>)//王子有单身
{
for (int j = M + ; j <= M + B; j++)
for (int i = ; i <= N; i++)
{
g[i][j] = ;
G[i].push_back(j + nx);
FG[j + nx].push_back(i);
}
}
if (A>)
{
for (int i = N + ; i <= N + A; i++)
for (int j = ; j <= M; j++)
{
g[i][j] = ;
G[i].push_back(j + nx);
FG[j + nx].push_back(i);
}
}
for (int i = ; i <= N; i++)
for (int j = ; j<Cun[i].size(); j++)
{
g[i][Cun[i][j]] = ;
G[i].push_back(Cun[i][j] + nx);
FG[Cun[i][j] + nx].push_back(i);
}
MaxMatch();
for (int i = ; i <= ny; i++)
if (cy[i] != -)
{
G[i + nx].push_back(cy[i]);
FG[cy[i]].push_back(i + nx);
} for (int i = ; i <= nx + ny; i++) if (!dfn[i]) dfs(i);
for (int i = ; i<nx + ny; i++) point[i].id = i + , point[i].dfn = dfn[i + ];
sort(point, point + nx + ny, cmp);
for (int i = ; i<nx + ny; i++)
if (!Belong[point[i].id])
Block++, Dfs(point[i].id);
int RT;
int ans[maxn];
printf("Case #%d:\n", er);
for (int i = ; i <= N; i++)
{
RT = ;
for (int j = ; j<Cun[i].size(); j++)
{
if (Belong[i] == Belong[Cun[i][j] + nx])
{
ans[RT] = Cun[i][j];
RT++;
}
}
printf("%d", RT);
for (int x = ; x<RT; x++) printf(" %d", ans[x]);
printf("\n");
}
}
return ;
}

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(匈牙利算法 连通分量)

    看了别人的题解.须要用到匈牙利算法的强连通算法 #include<cstdio> #include<algorithm> #include<vector> #pra ...

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

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

  6. Prince and Princess HDU - 4685(匹配 + 强连通)

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

  7. HDU4685:Prince and Princess(二分图匹配+tarjan)

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

  8. 强连通+二分匹配(hdu4685 Prince and Princess)

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

  9. POJ 1904 HDU 4685

    这两道题差不多,POJ这道我很久以前就做过,但是比赛的时候居然没想起来.. POJ 这道题的题意是,N个王子每个人都有喜欢的公主,当他们选定一个公主结婚时,必须是的剩下的人也能找到他喜欢的公主结婚. ...

随机推荐

  1. wcf使用ssl连接方式设置

    A.makecert -sr localmachine -ss My -n CN=TopupProxyServer -sky exchange -pe -r B.检索证书的指纹 ,证书名TopupPr ...

  2. 虚拟机 centos 7 nginx安装

    1下载vmware 12,并安装.百度即可 2下载centos 7,将其安装在vmware 12中.百度即可,无复杂设置. 3设置vmware 中centos7能上网: a.右键计算机->管理- ...

  3. c#设计模式-单例模式(面试题)

    c#设计模式-单例模式 单例模式三种写法: 第一种最简单,但没有考虑线程安全,在多线程时可能会出问题, public class Singleton { private static Singleto ...

  4. Xcode调试之查看变量

    从其他开发语言转行进军IOS开发的小伙伴可能会有这样一件苦恼的事情,调试程序时如何查看变量值?我并不喜欢每次都要通过打印去查看变量的值,也不喜欢通过光标悬浮到变量上来显示变量的值,如果要查看变量的属性 ...

  5. 七、oracle 表查询二

    1.使用逻辑操作符号问题:查询工资高于500或者是岗位为manager的雇员,同时还要满足他们的姓名首字母为大写的J?select * from emp where (sal > 500 or ...

  6. CodeFroces--Good Bye 2016-B--New Year and North Pole(水题-模拟)

    B. New Year and North Pole time limit per test 2 seconds memory limit per test 256 megabytes input s ...

  7. jsp之用户自定义标签

    创建一个类,引入外部jsp-api.jar包(在tomcat 下lib包里有),这个类继承SimpleTagSupport 重写doTag()方法. jspprojec包下的helloTag类: pu ...

  8. 瑞游天翼客户端win7,win8,win10

    以管理员身份运行即可, 链接: http://pan.baidu.com/s/1kTw7VH9 密码: vttq

  9. 怎么破解Wifi密码

    破解无络网络Wifi密码,让手机上Wifi不再受限. 方法/步骤 1 上网搜索并下载“Wfi万能钥匙”APK程序,然后将其安装到手机内存中.可以借助手机类管理软件将APK应用安装到手机中. 步骤阅读 ...

  10. ob_get_contents()

    ob_start();//buf1 echo 'multiple'; ob_start();//buf2 echo 'bufferswork'; $buf2 = ob_get_contents(); ...