1 二分图:
2 可以把图上所有点分成两个点集,且每条边均不在同一个点集的图。
3 如果环为二分图,那么边数一定是偶边。
4 显然若起点在A集合,则从A集合出发的点都是奇数边,从B集合连出的边都是偶数边,成环的二分图必然是从B连回A的,故边数为偶数,这也证明的奇环不是二分图;
5 二分图成环一定是偶数边,但是偶数边的环不一定是二分图如A->B->B-A->A五点四条边;
6 二分图是针对整张图的,所以染色过程中只要有一部分不是二分图,那么整张图就不是二分图;
7 题目leetcode785判断二分图 ,时间复杂度O(n+m)
8 class Solution {
9 public:
10 bool isBipartite(vector<vector<int>>& graph) {
11 int n=graph.size();
12 vector<int>G[n],f(n,0);
13 for(int i=0;i<n;i++)
14 for(auto &p:graph[i])G[i].push_back(p);
15 function<int(int,int)>dfs=[&](int u,int c)
16 {
17 f[u]=c;
18 for(auto &v:G[u])
19 {
20 if(f[v]==c)return 0;//如果u,v颜色相同说明在同一个点集
21 if(!f[v]&&!dfs(v,3-c))return 0;//否则的话去遍历没有访问过的点;
22 }
23 return 1;
24 };
25 for(int i=0;i<n;i++)
26 if(!f[i])if(!dfs(i,1))return false;//看每个连通块是否都满足二分图;
27 return true;
28 }
29 };
30
31 前置名词:
32 增广路:起点和终点都未被匹配的一条路径;
33 二分图最大匹配:匈牙利算法,核心思想是如果情敌有多个选择,与情敌商量,让情敌放弃,去追别人,让情敌匹配其他人去,如果能找到新匹配(增广路)
34 那么当前的请求被允许,否则拒绝当前请求;
35 题目洛谷3386 二分图最大匹配模板,时间复杂度O(n*m)
36 #include<bits/stdc++.h>
37 using namespace std;
38 const int N = 1000;
39 int n,m,e,cnt;
40 vector<int>v1[505];
41 int matched[1000],try_match[1000];
42
43 bool match(int u)
44 {
45 for(auto &v:v1[u])
46 {
47 if(!try_match[v])
48 {
49 try_match[v]=1;
50 if(!matched[v]||match(matched[v]))
51 {
52 matched[v]=u;
53 return true;
54 }
55 }
56 }
57 return false;
58 }
59 int main()
60 {
61 ios::sync_with_stdio(false);cin.tie(0);
62 cin>>n>>m>>e;
63 int u,v;
64 for(int i = 1; i <= e; i++)
65 {
66 cin>>u>>v;
67 v1[u].push_back(v);
68 }
69 for(int i = 1; i <= n; i++)
70 {
71 memset(try_match,0,sizeof(try_match));
72 if(match(i))cnt++;
73 }
74 cout<<cnt<<"\n";
75 return 0;
76 }