// 看了大半天也没看懂 8h左右 头看疼了。
// 直接贴博客:
https://www.cnblogs.com/BAJimH/p/10569418.html
http://www.csie.ntnu.edu.tw/~u91029/Matching.html
https://blog.csdn.net/qq_30974369/article/details/79819292
模板
1 #include<cstdio> 2 #include<queue> 3 using namespace std; 4 const int MAXN = 500+5; 5 const int MAXE = 124750*2+5; 6 7 int num; 8 int head[MAXN]; 9 struct node { 10 int v, next; 11 } edge[MAXE]; 12 13 inline void add(int x, int y) { 14 edge[num] = (node){y, head[x]}; 15 head[x] = num++; 16 } 17 18 int n, m; 19 int love[MAXN]; 20 int vis[MAXN], fa[MAXN], pre[MAXN]; 21 int tim, dfn[MAXN]; 22 queue<int> q; 23 24 inline int find(int x) { return x == fa[x] ? x : fa[x] = find(fa[x]); } 25 26 inline int LCA(int u, int v) { 27 ++tim; u = find(u), v = find(v); 28 while(dfn[u] != tim) { 29 dfn[u] = tim; 30 u = find(pre[love[u]]); 31 if(v) swap(u, v); 32 } 33 return u; 34 } 35 36 inline void Blossom(int x, int y, int lca) { 37 while(find(x) != lca) { 38 pre[x] = y, y = love[x]; 39 if(vis[y] == 2) vis[y] = 1, q.push(y); 40 if(find(x) == x) fa[x] = lca; 41 if(find(y) == y) fa[y] = lca; 42 x = pre[y]; 43 } 44 } 45 46 bool Aug(int s) { 47 for(int i = 1; i <= n; ++i) fa[i] = i, vis[i] = pre[i] = 0; 48 while(!q.empty()) q.pop(); 49 q.push(s); 50 vis[s] = 1; 51 while(!q.empty()) { 52 int u = q.front(); 53 q.pop(); 54 for(int i = head[u]; i != -1; i = edge[i].next) { 55 int v = edge[i].v; 56 if(find(u) == find(v) || vis[v] == 2) continue; 57 if(!vis[v]) { 58 vis[v] = 2; 59 pre[v] = u; 60 if(!love[v]) { 61 for(int x = v, lst; x; x = lst) { 62 lst = love[pre[x]]; 63 love[x] = pre[x]; 64 love[pre[x]] = x; 65 } 66 return true; 67 } 68 //else 69 vis[love[v]] = 1;/ 70 q.push(love[v]); 71 } 72 else { 73 int lca = LCA(u, v); 74 Blossom(u, v, lca); 75 Blossom(v, u, lca); 76 } 77 } 78 } 79 return false; 80 } 81 82 int solve() { 83 int ans = 0; 84 tim = 0; 85 for(int i = 1; i <= n; ++i) love[i] = 0; 86 for(int i = 1; i <= n; ++i) { 87 if(!love[i] && Aug(i)) ++ans; 88 } 89 return ans; 90 } 91 92 int main() { 93 while(scanf("%d%d", &n, &m) == 2) { 94 int num = 0; 95 for(int i = 1; i <= n; ++i) head[i] = -1; 96 int x, y; 97 for(int i = 0; i != m; ++i) { 98 scanf("%d%d", &x, &y); 99 add(x, y); add(y, x); 100 } 101 printf("%d ", solve()); 102 for(int i = 1; i <= n; ++i) { 103 if(i != 1) printf(" "); 104 printf("%d", love[i]); 105 } 106 printf(" "); 107 } 108 return 0; 109 }