暂时只包括与最大匹配相关的问题。

求最大独立集,最小路径覆盖等等大多数题目都可以转化为求最大匹配用匈牙利算法解决。

1.最大匹配(边集)

此类问题最直接,直接用匈牙利算法即可。

HDU 2063  过山车

http://acm.hdu.edu.cn/showproblem.php?pid=2063

二分图最大匹配模版题。

ZOJ 1654 - Place the Robots

http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=1654

易想到求最大独立集但是时间复杂度太高,可以变成二分图最大匹配来做,重在建模。

2.最小路径覆盖(边集)

对于不存在孤立的点的图,|最小路径覆盖|+|最大匹配|=V(顶点数)

因此可以通过求最大匹配来做。

这个等式在DAG图中也成立,详见http://www.cnblogs.com/jackiesteed/articles/2043934.html。对于DAG图可以拆点来做。

HDU 1151 Air Raid

http://acm.hdu.edu.cn/showproblem.php?pid=1151

 #include<iostream>
 #include<cstring>
 #include<cmath>
 #include<algorithm>
 #include<cstdlib>
 #include<cstdio>
 #include<vector>
 #define MAXN 1005
 using namespace std;
 bool gl[MAXN][MAXN];
 int link[MAXN];
 int n;
 bool vis[MAXN];

 bool match(int x)
 {
     ; i<=n; ++i)
         if(gl[x][i]&&!vis[i])
         {
             vis[i]=true;
             ||match(link[i]))
             {
                 link[i]=x;
                 return true;
             }
         }
     return false;
 }
 int main()
 {
     int T;
     scanf("%d",&T);
     while(T--)
     {  int m;
         scanf("%d%d",&n,&m);
         memset(gl,,sizeof(gl));
         ;i<m;++i)
         {
             int x,y;
             scanf("%d%d",&x,&y);
             gl[x][y]=true;
         }
         ;
         memset(link,-,sizeof(link));
         ; i<=n; ++i)
         {
             memset(vis,,sizeof(vis));
             if(match(i)) res++;
         }
         printf("%d\n",n-res);
     }
     ;
 }

求DAG的最小路径覆盖。

3.最小顶点覆盖(点集)

在二分图中|最大匹配|=|最小顶点覆盖|,但是注意要解决的问题本身并不是最大匹配,理解了问题本身才能建模。

HDU 1054  Strategic Game

http://acm.hdu.edu.cn/showproblem.php?pid=1054

此题可以用树形DP来做也可以用求最小顶点覆盖,但是时间较慢。拆点,改成双向图,用邻接表。

#include<iostream>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<cstdlib>
#include<cstdio>
#include<vector>
#define MAXN 1505
using namespace std;
vector<int> gl[MAXN];
int link[MAXN];
int n;
bool vis[MAXN];
void init()
{
    memset(link,-,sizeof(link));
    memset(vis,,sizeof(vis));
}

bool match(int x)
{
    ; i<gl[x].size(); ++i)
    {
        int &u=gl[x][i];
        if(!vis[u])
        {
            vis[u]=true;
            ||match(link[u]))
            {
                link[u]=x;
                return true;
            }
        }
    }

    return false;
}
int main()
{
    while(scanf("%d",&n)!=EOF)
    {
        memset(gl,,sizeof(gl));
        ; i<n; ++i)  gl[i].clear();
        ; i<n; ++i)
        {
            int now,t,cn;
            scanf("%d:",&now);
            scanf("(%d)",&cn);
            while(cn--)
            {
                scanf("%d",&t);
                gl[now].push_back(t);
                gl[t].push_back(now);
            }
        }
        init();
        ;
        ; i<n; ++i)
        {
            memset(vis,,sizeof(vis));
            if(match(i)) res++;
        }
        printf();
    }
    ;
}

HDU 1150  Machine Schedule

http://acm.hdu.edu.cn/showproblem.php?pid=1150

#include<iostream>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<cstdlib>
#include<cstdio>
#include<vector>
#define MAXN 1005
using namespace std;
bool gl[MAXN][MAXN];
int link[MAXN];
int n,m;
bool vis[MAXN];

bool match(int x)
{
    ; i<=m; ++i)
        if(gl[x][i]&&!vis[i])
        {
            vis[i]=true;
            ||match(link[i]))
            {
                link[i]=x;
                return true;
            }
        }
    return false;
}
int main()
{
    int t;
    while(scanf("%d",&n)&&n)
    {
        scanf("%d%d",&m,&t);
        memset(gl,,sizeof(gl));
        ; i<t; ++i)
        {
            int x,y,z;
            scanf("%d%d%d",&z,&x,&y);
            gl[x][y]=true;
        }
        ;
        memset(link,-,sizeof(link));
        ; i<=n; ++i)
        {
            memset(vis,,sizeof(vis));
            if(match(i)) res++;
        }
        printf("%d\n",res);
    }
    ;
}

4.最大独立集(点集)

|最大独立集|+|最小顶点覆盖|=V

求最大独立集是NP问题,但是在二分图中|最大匹配|=|最小顶点覆盖|,所以这个问题也有了高效的算法。

HDU 1045  Fire Net

http://acm.hdu.edu.cn/showproblem.php?pid=1045

这个可以暴力求最大独立集。

HDU 2768  Cat vs. Dog

http://acm.hdu.edu.cn/showproblem.php?pid=2768

根据矛盾之间建图,求最大独立集。

HDU 1068  Girls and Boys

http://acm.hdu.edu.cn/showproblem.php?pid=1068

题意很明显就是求二分图最大独立集。但是由于没说给的是男还是女,所以需要拆点,得到的最大匹配数要除以2,再套用公式得最大独立集。

 #include<iostream>
 #include<cstring>
 #include<cmath>
 #include<algorithm>
 #include<cstdlib>
 #include<cstdio>
 #include<vector>
 #define MAXN 1005
 using namespace std;
 bool gl[MAXN][MAXN];
 int link[MAXN];
 int n;
 bool vis[MAXN];
 void init()
 {
     memset(link,-,sizeof(link));
     memset(vis,,sizeof(vis));
 }

 bool match(int x)
 {
     ; i<n; ++i)
         if(gl[x][i]&&!vis[i])
         {
             vis[i]=true;
             ||match(link[i]))
             {
                 link[i]=x;
                 return true;
             }
         }
     return false;
 }
 int main()
 {
     while(scanf("%d",&n)!=EOF)
     {
         memset(gl,,sizeof(gl));
         ; i<n; ++i)
         {
             int now,t,cn;
             scanf("%d: ",&now);
             scanf("(%d) ",&cn);
             while(cn--)
             {
                 scanf("%d",&t);
                 gl[now][t]=true;
             }
         }
         init();
         ;
         ; i<n; ++i)
         {
             memset(vis,,sizeof(vis));
             if(match(i)) res++;
         }
         printf(-res)/);
     }
     ;
 }

5.判断二分图

此类问题可以BFS或DFS解决,注意图可能不连通。

HDU 4751 Divide Groups

http://acm.hdu.edu.cn/showproblem.php?pid=4751

根据不互相认识这一关系连边,判断二分图。

ACM -二分图题目小结的更多相关文章

  1. ACM - KMP题目小结 (更新中)

    KMP算法题型大致有两类,一类是next数组的应用,一类是匹配问题. next数组大多数是求字符串周期,或者是与前缀后缀有关,也可以应用在DP中.需要对next数组有一定理解才能做得出. next数组 ...

  2. ACM - 概率、期望题目 小结(临时)

    概率DP求期望大多数都是全期望公式的运用.主要思考状态空间的划分以及状态事件发生的概率.问题可以分为无环和有环两类.无环一类多数比较简单,可以通过迭代或者记忆化搜索完成.有环一类略复杂,可以通过假设方 ...

  3. 【Mark】博弈类题目小结(HDU,POJ,ZOJ)

    转载请注明出处,谢谢http://blog.csdn.net/ACM_cxlove?viewmode=contents    by---cxlove 首先当然要献上一些非常好的学习资料: 基础博弈的小 ...

  4. ACM计算几何题目推荐

    //第一期 计算几何题的特点与做题要领: 1.大部分不会很难,少部分题目思路很巧妙 2.做计算几何题目,模板很重要,模板必须高度可靠. 3.要注意代码的组织,因为计算几何的题目很容易上两百行代码,里面 ...

  5. ACM一些题目

    Low Power 先二分答案,可以通过调整证明同一台机器选的两个芯片必然是提供能量数值相邻的两个.所以再贪心一下就可以了. 时间复杂度\(O(n \log n)\). Factors 假设\(k\) ...

  6. CDQ分治题目小结

    CDQ分治属于比较特殊的一类分治,许多问题转化为这类分治的时候,时空方面都会有很大节省,而且写起来没有这么麻烦. 这类分治的特殊性在于分治的左右两部分的合并,作用两部分在合并的时候作用是不同的,比如, ...

  7. 2015暑假acm短训小结

    时间很快,短训已经结束,短短20天,心里有一些思绪想要记下. 收获: 从最近发的随笔中可以看出,做得最多的是搜索——Dfs,Bfs.对于搜索,如何描述状态,如何压缩状态,如何决定下一个结点,是否可以剪 ...

  8. codeforeces近日题目小结

    题目源自codeforeces的三场contest contest/1043+1055+1076 目前都是solved 6/7,都差了最后一题 简单题: contest/1043/E: 先不考虑m个限 ...

  9. ACM 字符串 题目整理

    AC自动机 UVa 11468  Substring AC自动机+概率DP. 注意要补全不存在的边. 为什么要补全不存在的边呢?补全以后可以直接找到状态的转移,即从所有子节点就可以实现所有状态转移. ...

随机推荐

  1. Android SQlite详解

    在项目开发中,我们或多或少都会用到数据库.在Android中,我们一般使用SQLite,因为Android在android.database.sqlite包封装了很多SQLite操作的API.我自己写 ...

  2. osx 10.11.5 El Capitan U盘制作安装

    osx 10.11.5 El Capitan U盘制作安装 1. 下载osx10.11.5 从mac的 appstore下载(官方原版) 2. U盘8G起(注意备份重要资料) 3. 下载完成之后在Fi ...

  3. The Network Adapter could not establish the connection问题研究

    最近一个项目会报上述错误,但也不是经常发生,所以很难跟踪,影响不是很大,但每次看到日志中这个错误就会不舒服,还是要想办法解决才是. 错误提示信息很明确是网络适配器不能创建连接. 查了很多资料,并且Or ...

  4. ajax再接触

    贴三个目前写的已经工作了的ajax,并且给出备注: 1.这是第一个ajax以及它的接口文档,需要注意的是1.因为返回数据是xml所以多加了contentType:"application/x ...

  5. 双日历插件--jq datepicker时间范围选择

    <!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8&quo ...

  6. word-break:break-all和word-wrap:break-word的区别

    了解word-break属性 /* 关键字值 */ word-break: normal; word-break: break-all; word-break: keep-all; /* 全局值 */ ...

  7. 谈谈JPA-01-概述

    JPA和Hibernate的关系 JPA 是 hibernate 的一个抽象(就像JDBC和JDBC驱动的关系): JPA 是规范:JPA 本质上就是一种  ORM 规范,不是ORM 框架 —— 因为 ...

  8. 《Java程序设计》第八周学习总结

    20145224 <Java程序设计>第八周学习总结 教材学习内容总结 第15章 通用API 15.1.1 日志API简介 ·java.util.logging包提供了日志功能相关类与接口 ...

  9. NSNotification系统通知优化

    最近在github上看到了LRNotificationObserver这个项目,看了一下实现方式,作者通过ARC机制实例化注册对象子类与关联对象的方法来管理注册对象的生命周期.从而省去了系统通知移除的 ...

  10. Linux基础: 系统加载过程和运行级别含义

    BIOS 有固化代码指向mbr,mbr指向grub(/boot/grub/下有很多引导配置信息),grub里可以配置多种linux内核vmlinux文件. 启动内核以后就开始加载各种驱动模块并进行系统 ...