zoukankan      html  css  js  c++  java
  • 二分图最大匹配模板【代码注释版】

    本文为代码注释版
    默认读者已经了解二分图食用方式
    适于复习 或最后一轮学习食用
    本代码为洛谷3386【模板】二分图匹配 AC代码

    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    using namespace std;
    const int N = 1005;
    bool road[N][N], used[N];
    int match[N], n, m, e;
    /*
    关于定义
    road[i][j] == 1表示左边集合中的i到右边集合中的j有边
    used[i] == 1是在每次做增广的时候记录已访问右集合的节点i
    match[i]记录右集合节点j的匹配对象
    n, m, e如题 (左集合大小,右集合大小, 边数)
    */
    bool dfs(int x){
         for(int i = 1; i <= m; ++i)
             if(!used[i] && road[x][i]){                     //判断这条边是否可以走
                 used[i] = 1;                                     //记录这个节点已经被访问 防止成环
                 if(!match[i] || dfs(match[i])){            //如果这个点可以被让出来
                     match[i] = x; return 1;                 //记录新的匹配点 返回true
                 }        
             }    
         return 0;                                                  //匹配失败
    }
    int main(){
        scanf("%d%d%d", &n, &m, &e);
        for(int i = 1, x, y; i <= e; ++i){
            scanf("%d%d", &x, &y);
            if(x <= n && y <= m) road[x][y] = 1;      //注意题目中说到有不合法的边  
        }
        int ans = 0;                                                //答案
        for(int i = 1; i <= n; ++i){
            for(int j = 1; j <= m; ++j) used[j] = 0;      //每次查询前都要清空used
            if(dfs(i)) ++ans;                                      //如果这个点可以找到匹配点的话 答案加一
        } 
        printf("%d", ans);
        return 0;
    }
    
    
  • 相关阅读:
    UVA 12338
    最短路问题
    菜鸟调错(十)——启动Tomcat报错“Unsupported major.minor version xxx ”
    Servlet总结(一)
    <html>
    Android Developer:Allocation Tracker演示
    H2数据库集群
    安卓通过广播自己主动回填短信验证码
    江湖问题研究-- intent传递有没有限制大小,是多少?
    spring 配置文件被加载两次
  • 原文地址:https://www.cnblogs.com/hjmmm/p/9996174.html
Copyright © 2011-2022 走看看