题解 George and Interesting Graph
George 喜欢图,因此它想让图更有趣。他认为有趣的图满足以下条件:
- 没有重边;
- 存在且仅存在一个结点 $v$(称为中心),使得对于图中的任意结点 $u$,都有边 $(u,v)$ 和 $(v,u)$,注意自环 $(v,v)$ 也应该存在;
- 除去中心外,每个点的入度和出度都恰好为 $2$;
显然很少有图有趣,但 George 可以把图变得有趣:每次他可以增加一条边或者删除一条已经存在的边。
现在给出图 $G$,George 想知道他最少做多少次操作可以使它变得有趣。$ 2 \le n \le 500,1 \le m \le 1000 $
第一次看到这道题的时候感觉一点思路都没有, 但是注意到 $1 \le n \le 100$
所以我们可以枚举 $n$。考虑第 $i$ 个点作为中心时, 把这个图变为有趣的图的贡献。首先我们计算将与中心相连的边补齐的贡献,发现余下的点还需要一个入度,出度。容易想到把余下的点拆成入读点和出度点,然后对于一条 $u - v$ 的边将 $u$ 的出度点 连向 $v$ 的入度点。然后求二分图最大匹配数 $sum$,即可以直接拿来用的边的数量。用边数减去 $sun$ 得到删去边的数量。综合所有情况取 $min$ 即可。
$Code$
#include<bits/stdc++.h>
using namespace std;
#define rp(i, a, b) for(int i = a;i <= b;i++)
const int N = 1050;
const int M = 2005;
struct edge {int next, to;} e[M << 1];
int cnt, tim, n, m;
int head[N], match[N], vis[N];
int Map[N][N];
void add(int f, int t) {
    e[++cnt] = edge{head[f], t}, head[f] = cnt;
    e[++cnt] = edge{head[t], f}, head[t] = cnt;
}
int dfs(int u, int k) {
    if(u == k) return 0;
    for(int i = head[u];i;i = e[i].next) {
        int v = e[i].to;
        if(!(vis[v] - tim) || v == k || v == k + n) continue;
        //cerr << u << " " << v << " " << k << endl;
        vis[v] = tim; 
        if(!match[v] || dfs(match[v], k)) {
            match[v] = u;
            return 1;
        }
    }
    return 0;
}
int main(){
    scanf("%d %d", &n, &m);
    rp(i, 1, m) {
        int u, v;
        scanf("%d %d", &u, &v);
        add(u + n, v);
        Map[u][v] = 1; 
    }
    int ans = 1e9;
    rp(k ,1, n) {
        memset(match, 0 ,sizeof match);
        int sum = 0, dl = 0, ddt = 0;
        ddt += !Map[k][k];
        rp(i, 1, n) if(i != k) ddt += !Map[i][k] + !Map[k][i];
        rp(i, 1, n) rp(j, 1, n) if(i != k && j != k) dl += Map[i][j];
        rp(i, 1, n) {
            //cerr << "st" << i << " " << k << endl;
            if(i == k) continue; 
            tim++;
            if(dfs(i, k)) sum++;
        }
        //cerr << k << " " << sum << " " << ddt << " " << dl << endl;
        ans = min(ans, ddt + ((n - 1) - sum) + (dl - sum)); 
    }
    printf("%d", ans);
    return 0;
} 
                    
                
 
                
            
         浙公网安备 33010602011771号
浙公网安备 33010602011771号