zoukankan      html  css  js  c++  java
  • [HDOJ6178]Monkeys(二分图最大匹配)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6178

    题意:希望在一棵树中删掉最多的边,使得剩下的k个点至少有一个点相连。

    比赛时候学弟贪心dfs过的,然后发现这个题实际上是最大匹配。

    任意两点相连代表匹配中的一条边,最大匹配后的结果就是树上最多有多少点对两两有边。

    考虑最大匹配Max>=k的时候,直接两两配对即可,答案就是k/2取上整。

    Max<k的时候就是k-Max/2取下整。

    朝鲜也流行卡常啊?我夸夸你们啊?

      1 #include <bits/stdc++.h>
      2 using namespace std;
      3 
      4 typedef struct Edge { int v, next; }Edge;
      5 const int maxn = 100005;
      6 const int inf = 0x3f3f3f3f;
      7 int nx, ny, dist;
      8 int Mx[maxn], My[maxn], dx[maxn], dy[maxn], vis[maxn];
      9 int head[maxn], ecnt;
     10 Edge edge[maxn<<1];
     11 
     12 int n, m;
     13 void init() {
     14     memset(head, -1, sizeof(head));
     15     for(int i = 0; i < maxn; i++) edge[i].next = -1;
     16     ecnt = 0;
     17 }
     18 
     19 void adde(int u, int v) {
     20     edge[ecnt].v = v;
     21     edge[ecnt].next = head[u]; head[u] = ecnt++;
     22 }
     23 
     24 bool Dfs(int u) {
     25     for(int i = head[u]; ~i; i=edge[i].next) {
     26         int& v = edge[i].v;
     27         if(!vis[v] && dy[v] == dx[u] + 1) {
     28             vis[v] = 1;
     29             if(My[v] != -1 && dy[v] == dist) continue;
     30             if(My[v] == -1 || Dfs(My[v])) {
     31                 My[v] = u;
     32                 Mx[u] = v;
     33                 return 1;
     34             }
     35         }
     36     }
     37     return 0;
     38 }
     39 bool Search() {
     40     queue<int> Q;
     41     dist = inf;
     42     memset(dx, -1, sizeof(dx));
     43     memset(dy, -1, sizeof(dy));
     44     for(int i = 0; i < nx; i++) {
     45         if(Mx[i] == -1) {
     46             Q.push(i), dx[i] = 0;
     47         }
     48     }
     49     while(!Q.empty()) {
     50         int u = Q.front();
     51         if(dx[u] > dist) break;
     52         Q.pop();
     53         for(int i = head[u]; ~i; i=edge[i].next) {
     54             int& v = edge[i].v;
     55             if(dy[v] == -1) {
     56                 dy[v] = dx[u] + 1;
     57                 if(My[v] == -1) dist = dy[v];
     58                 else {
     59                     dx[My[v]] = dy[v] + 1;
     60                     Q.push(My[v]); 
     61                 }
     62             }
     63         }
     64     }
     65     return dist != inf;
     66 }
     67 
     68 int MaxMatch() {
     69     int res = 0;
     70     memset(Mx, -1, sizeof(Mx));
     71     memset(My, -1, sizeof(My));
     72     while(Search()) {
     73         memset(vis, 0, sizeof(vis));
     74         for(int i = 0; i < nx; i++) {
     75             if(Mx[i] == -1 && Dfs(i)) res++;
     76         }
     77     }
     78     if(res >= m) return (m + 1) / 2;
     79     else return m - res / 2;
     80 }
     81 
     82 namespace fastIO {
     83     #define BUF_SIZE 100000
     84     //fread -> read
     85     bool IOerror = 0;
     86     inline char nc() {
     87         static char buf[BUF_SIZE], *p1 = buf + BUF_SIZE, *pend = buf + BUF_SIZE;
     88         if (p1 == pend) {
     89             p1 = buf;
     90             pend = buf + fread(buf, 1, BUF_SIZE, stdin);
     91             if (pend == p1) {
     92                 IOerror = 1;
     93                 return -1;
     94             }
     95         }
     96         return *p1++;
     97     }
     98     inline bool blank(char ch) {
     99         return ch == ' ' || ch == '
    ' || ch == '
    ' || ch == '	';
    100     }
    101     inline void read(int &x) {
    102         char ch;
    103         while (blank(ch = nc()));
    104         if (IOerror)
    105             return;
    106         for (x = ch - '0'; (ch = nc()) >= '0' && ch <= '9'; x = x * 10 + ch - '0');
    107     }
    108     #undef BUF_SIZE
    109 };
    110 
    111 
    112 signed main() {
    113     // freopen("in", "r", stdin);
    114     int T, u;
    115     fastIO::read(T);
    116     while(T--) {
    117         init();
    118         fastIO::read(n); fastIO::read(m);
    119         nx = ny = n;
    120         for(int i = 2; i <= n; i++) {
    121             fastIO::read(u);
    122             adde(u-1, i-1), adde(i-1, u-1);
    123         }
    124         printf("%d
    ", MaxMatch());
    125     }
    126     return 0;
    127 }

  • 相关阅读:
    设计模式之-工厂模式、构造函数模式
    发布订阅小示例
    使用vue,react,angular等框架和不使用框架使用jquery的优缺点
    react优化--pureComponent
    Vue、 React比较
    ORACLE触发器和new、old特殊变量
    mysql的存储过程与自定义函数
    MySQL日期
    php(Personal Home Page)简介,安装和配置(apache服务器使用和配置1)
    话谈html语义化
  • 原文地址:https://www.cnblogs.com/kirai/p/7424880.html
Copyright © 2011-2022 走看看