//二分图最大匹配 匈牙利算法
#include <cstdio>
using namespace std;
const int N = 510;
int e[N][N];
int match[N];//记录配对关系 比如u->v记作match[v]=u
int book[N];
int n, m;
bool dfs(int u) {
for (int i = 1; i <= n; ++i) {
if (book[i] == 0 && e[u][i] == 1) {
book[i] = 1; //标记点i已访问过
//如果点i未配对或找到了新的配对点
if (match[i] == 0 || dfs(match[i])) {
//更新配对关系
match[i] = u;
return true;
}
}
}
return false;
}
int main() {
int t1, t2, sum = 0;
scanf("%d%d", &n, &m); //n个点m条边
memset(e, 0, sizeof(e));
for (int i = 1; i <= m; ++i) {
scanf("%d%d", &t1, &t2);
e[t1][t2] = 1;
}
memset(match, 0, sizeof(match));
for (int i = 1; i <= n; ++i) {
memset(book, 0, sizeof(book));//清空上次搜索时的标记
if (dfs(i)) sum++; //寻找增广路,如果找到,配对数加1
}
printf("%d\n", sum);
return 0;
}
/*
3 5
1 1
1 2
2 2
2 3
3 1
3
*/
二分图匹配题目 羊吃草
链接:https://ac.nowcoder.com/acm/problem/25151
来源:牛客网
题目描述
有一个草原可以用一个1~400的数轴表示。有n头羊和q个查询。每头羊的编号分别是1,2,3…n。第i头羊只喜爱数轴上[ai,bi]这样的一个闭区间,每一时刻每头羊只可能在自己喜爱的区间的某个点上吃草。现在给出q个查询,每个查询两个整数l,r。你需要计算出在同一时刻,最多能有多少头羊同时在这个区间内吃草。数轴上每一个整点同一时刻只能容纳一只羊,羊只会在整点吃草。
输入描述:
第一行三个数n q。
第二行n个数a1 a2…an。
第三行n个数b1 b2…bn。
接下来q行每行两个数l,r。表示询问的区间。
输出描述:
对于每个查询,输出一个整数表示答案。
输入
5 3
1 1 1 2 4
1 1 1 3 5
1 5
2 5
1 3
输出
3
2
2
备注:
1<=n,q<=400
1<=ai<=bi<=400
1=l<=r<=400
/*AC代码一*/
#include <cstdio>
#include <cstring>
#include <vector>
using namespace std;
const int N = 402;
int n, q, a[N], b[N];
vector<int> G[N]; //vector存图
int match[N];
bool vis[N];
bool dfs(int u) {
vis[u] = true;
for (int i = 0; i < G[u].size(); i++) {
int v = G[u][i];
if (match[v] == 0 || (!vis[match[v]] && dfs(match[v]))) {
match[v] = u;
return true;
}
}
return false;
}
int main() {
scanf("%d%d", &n, &q);
for (int i = 1; i <= n; i++) {
scanf("%d", &a[i]);
}
for (int i = 1; i <= n; i++) {
scanf("%d", &b[i]);
for (int j = a[i]; j <= b[i]; j++) {
G[j].push_back(i);
}
}
while (q--) {
int l, r, ans = 0;
memset(match, 0, sizeof(match));
scanf("%d%d", &l, &r);
for (int i = l; i <= r; i++) {
memset(vis, false, sizeof(vis));
if (dfs(i)) ans++;
}
printf("%d\n", ans);
}
return 0;
}
/*AC代码二*/
#include <cstdio>
#include <cstring>
using namespace std;
int a[404], b[404];
int e[404][404]; //邻接矩阵存图
int match[404];
int book[404];
int n, m;
bool dfs(int u) {
for (int i = 1; i <= n; ++i) {
if (book[i] == 0 && e[u][i] == 1) {
book[i] = 1;
if (match[i] == 0 || dfs(match[i])) {
match[i] = u;
return true;
}
}
}
return false;
}
int main() {
int t1, t2;
scanf("%d%d", &n, &m);
for (int i = 1; i <= n; ++i) {
scanf("%d", &a[i]);
}
for (int i = 1; i <= n; ++i) {
scanf("%d", &b[i]);
for (int j = a[i]; j <= b[i]; ++j) {
e[j][i] = 1;
}
}
while (m--) {
int l, r, sum = 0;
memset(match, 0, sizeof(match));
scanf("%d%d", &l, &r);
for (int i = l; i <= r; ++i) {
memset(book, 0, sizeof(book));
if (dfs(i)) {
sum++;
}
}
printf("%d\n", sum);
}
return 0;
}