匈牙利算法
A公司和B公司有n个合作的子项目,每个子项目由A公司和B公司各一名员工参与。一名员工可以参与多个子项目。
一个员工如果担任了该项目的项目经理,它需要对所参与的该项目负责。一个员工也可以负责多个项目。
A公司和B公司需要保证所有子项目都能有人负责,问最少需要指定几名项目经理?----网易校招笔试题
Solution:
此问题属于二分图中最小点覆盖(或者最大匹配边数)的问题
import java.util.*;
public class Main{
public static void main(String[] args) {
Scanner s = new Scanner(System.in);
int[] A = getArr(s.nextLine().trim());
int[] B = getArr(s.nextLine().trim());
int n = Integer.parseInt(s.nextLine().trim());
int[] p = new int[10000];
int[][] map = new int[10000][10000];
for(int i = 0; i < n; i++) {
int[]tmp = getArr(s.nextLine().trim());
map[tmp[0]][tmp[1]] = 1;
}
Arrays.fill(p, - 1);
boolean[] visit = new boolean[10000];
int cnt = 0;
for(int i: A) {
Arrays.fill(visit, false);
if(match(i, map, visit, B, p)) {
cnt++;
}
}
System.out.println(cnt);
}
public static int[] getArr(String str) {
String[] arr = str.split(" ");
int[] res = new int[arr.length];
for(int i = 0; i < arr.length; i++) {
res[i] = Integer.parseInt(arr[i]);
}
return res;
}
public static boolean match(int i, int[][] map, boolean[] visit, int[] B, int[] p) {
for (int j = 0; j < B.length ; j++) {
if(map[i][B[j]] != 0 && !visit[B[j]]) {
visit[B[j]] = true;
if(p[B[j]] == -1 || match(p[B[j]], map, visit, B, p)) {
p[B[j]] = i;
return true;
}
}
}
return false;
}
}