HDU 2444 The Accomodation of Students【二分图染色+匹配*好题】

来源:互联网 发布:八字不合怎么办知乎 编辑:程序博客网 时间:2024/06/05 08:30

题目链接

题意:编号1~n,给你几组互为朋友的关系。现在让你分两组,且同一组的人之间不能认识。如果可以分配,现在让你分方间,同一房间的人为朋友住双人间,问你需要多少双人间,不可以分配就No.

思路:分两组可以进行简单的二分图染色,分房间时就是最大匹配了。但是我却wa着过的,建图时需要注意:原来的编号没变,所以,已经在左端匹配的编号i,不能在另一组继续匹配了(或者不加标识,直接结果除2,都是同样的道理).

#include <cstdio>#include <cstring>#include <algorithm>#include <vector>#include <cmath>#include <queue>using namespace std;const int MAXN = 200 + 10;int ma[MAXN][MAXN];int vis[MAXN];vector<int> v[MAXN];bool dfs(int x, int col) {    vis[x] = col;    for(int i = 0; i < v[x].size(); i++) {        int cnt = v[x][i];        if(vis[cnt] == vis[x]) return false;        else if(vis[cnt] == -1 && !dfs(cnt, !col)) return false;    }    return true;}int n, m, p1, p2;int cx[MAXN], cy[MAXN];bool bmask[MAXN];int findpath(int u) {    for(int i = 1; i <= n; i++) {        if(ma[u][i] && !bmask[i]) {            bmask[i] = 1;            if(cy[i] == -1 || findpath(cy[i])) {                cy[i] = u; //板子需要修改的一个地方                 cy[u] = i;                cx[u] = i;                cx[i] = u;                return 1;            }        }    }    return 0;}int Max_Match() { //最大匹配     int res = 0;    for(int i = 0; i<= n; i++) {        cx[i] = -1;        cy[i] = -1;    }    for(int i = 1; i <= n; i++)  {        if(cx[i] == -1) {            memset(bmask, 0, sizeof(bmask));            res += findpath(i);        }    }//  for(int i = 1; i <= ny; i++) {//      printf("%d -> %d\n", i, cy[i]);//  }     return res;}void init() {    memset(ma, 0, sizeof(ma));    memset(vis, -1, sizeof(vis));    for(int i = 0; i < MAXN; i++) {        v[i].clear();    }}int main() {    while(scanf("%d %d", &n, &m) != EOF) {        init();        bool flag = true;        for(int i = 1; i <= m; i++) {            scanf("%d %d", &p1, &p2);            v[p1].push_back(p2);            v[p2].push_back(p1);            ma[p1][p2] = 1;            ma[p2][p1] = 1;        }        for(int i = 1; i <= n; i++) {            if(vis[i] == -1 && !dfs(i, 0)) {                flag = false;                break;            }        }        if(!flag) {            printf("No\n");            continue;        }        printf("%d\n", Max_Match());    }    return 0;} /*Sample Input4 41 21 31 42 36 51 21 31 42 53 6Sample OutputNo3*/
阅读全文
1 0
原创粉丝点击