• poj1422 Air Raid 二分匹配之最小路径覆盖


    http://poj.org/problem?id=1422

    典型的最小路径覆盖题,城市之间单向相连,无环!问最少用多少个伞兵能遍历这张图。
    根据定理:最小路径覆盖=顶点数-最大匹配数

    Source Code
    #include<stdio.h>
    #include<stdlib.h>
    #include<string.h>
        int nx, ny;             // X的點數目、Y的點數目
    int mx[121], my[121];   // X各點的配對對象、Y各點的配對對象
    bool vy[121];           // 紀錄Graph Traversal拜訪過的點
    bool adj[121][121];     // 精簡過的adjacency matrix
    // 以DFS建立一棵交錯樹
    bool DFS(int x)
    {
        for (int y=0; y<ny; ++y)
            if (adj[x][y] && !vy[y])
            {
                vy[y] = true;
                // 找到擴充路徑
                    if (my[y] == -1 || DFS(my[y]))
                {
                    mx[x] = y; my[y] = x;
                    return true;
                   }
            }
        return false;
    }
    int bipartite_matching()
    {
        // 全部的點初始化為未匹配點。
        memset(mx, -1, sizeof(mx));
            memset(my, -1, sizeof(my));
        // 依序把X中的每一個點作為擴充路徑的端點,
        // 並嘗試尋找擴充路徑。
        int c = 0;
        for (int x=0; x<nx; ++x)
    //     if (mx[x] == -1)    // x為未匹配點,這行可精簡。
            {
                // 開始Graph Traversal
                memset(vy, false, sizeof(vy));
                if (DFS(x)) c++;
            }
        return c;
    }
    main()
    {
              int i,a,b,t,n,m;
              scanf("%d",&t);
              while(t--)
              {
                scanf("%d%d",&n,&m);
                memset(adj,0,sizeof(adj));
                for(i=0;i<m;i++)
                {
                  scanf("%d%d",&a,&b);
                  adj[a-1][b-1]=1;
                }
                nx=ny=n;
                printf("%d\n",n-bipartite_matching());
              }
              system("pause");
    }

  • 相关阅读:
    PHP登入
    PHP注册
    PHP数据访问
    php实现人员的权限管理
    PHP实现简单的评论与回复功能还有删除信息
    php文件的管理
    文件的操作
    文件上传及预览
    ajax分页
    三级联动
  • 原文地址:https://www.cnblogs.com/zxj015/p/2740293.html
Copyright © 2020-2023  润新知