标签:输出 NPU 相互 inpu return nal diff tar icpc
标签: 最大独立集 最小路径覆盖
In this problem, we would like to talk about unreachable sets of a directed acyclic graph G = (V, E). In mathematics a directed acyclic graph (DAG) is a directed graph with no directed cycles. That is a graph such that there is no way to start at any node and follow a consistently-directed sequence of edges in E that eventually loops back to the beginning again.
A node set denoted by V UR ? V containing several nodes is known as an unreachable node set of G if, for each two different nodes u and v in V UR , there is no way to start at u and follow a consistently-directed sequence of edges in E that ?nally archives the node v. You are asked in this problem to calculate the size of the maximum unreachable node set of a given graph G.
The input contains several test cases and the first line contains an integer T (1 ≤ T ≤ 500) which is the number of test cases.
For each case, the first line contains two integers n (1 ≤ n ≤ 100) and m (0 ≤ m ≤ n(n ? 1)/2) indicating the number of nodes and the number of edges in the graph G. Each of the following m lines describes a directed edge with two integers u and v (1 ≤ u, v ≤ n and u != v) indicating an edge from the u-th node to the v-th node. All edges provided in this case are distinct.
We guarantee that all directed graphs given in input are DAGs and the sum of m in input is smaller than 500000.
For each test case, output an integer in a line which is the size of the maximum unreachable node set of G.
3
4 4
1 2
1 3
2 4
3 4
4 3
1 2
2 3
3 4
6 5
1 2
4 2
6 2
2 3
2 5
样例输出
2
1
3
给定一个DAG,求出此图满足以下条件的最大点集合:集合中任意两点相互不可达。
先求出DAG的闭包,然后闭包的最大独立集即为所求,DAG的闭包满足性质
\[最大独立集 = 最小路径覆盖 \]
// Ford-fulkerson算法
#include <iostream>
#include <cstdio>
#include <cstring>
#include <queue>
using namespace std;
typedef long long ll;
const ll MOD=1e9+7;
const int maxn=100050;
const int inf=0x3f3f3f3f;
int n,m;
bool a[150][150];
struct Edge
{
    int v,nxt,f,c;
}e[maxn];
int h[maxn],tot=1;
void addEdge(int x,int y,int w){
    e[++tot]=(Edge){y,h[x],0,w};
    h[x]=tot;
}
int s,t;
bool vis[250];
int dfs(int x,int flow){
    if(vis[x]||flow==0) return 0;
    vis[x]=true;
    if(x==t){
        return flow;
    }
    int ans=0;
    for (int i = h[x]; i ; i=e[i].nxt)
    {
        int t=min(flow,e[i].c-e[i].f);
        if(t>0&&(ans=dfs(e[i].v,t))){
            e[i].f+=ans;
            return ans;
        }
        t=min(flow,e[i^1].f);
        if(t>0&&(ans=dfs(e[i].v,t))){
            e[i^1].f-=ans;
            return ans;
        }
    }
    return 0;
}
int main(int argc, char const *argv[])
{
    int T;
    scanf("%d", &T);
    while(T--){
        scanf("%d%d", &n,&m);
        memset(a,false,sizeof a);
        memset(h,0,sizeof h);
        for (int i = 0; i < m; ++i)
        {
            int x,y;
            scanf("%d%d", &x,&y);
            if(x>=1&&x<=n&&y>=1&&y<=n) a[x][y]=true;
        }
        tot=1;
        for (int k = 1; k <= n; ++k)
        {
            for (int i = 1; i <= n; ++i)
            {
                for (int j = 1; j <= n; ++j)
                {
                    a[i][j]|=(a[i][k]&a[k][j]);
                }
            }
        }
        s=0,t=2*n+1;
        for (int i = 1; i <= n; ++i)
        {
            addEdge(s,i,1);
            addEdge(i,s,0);
            addEdge(i+n,t,1);
            addEdge(t,i+n,0);
            for (int j = 1; j <= n; ++j)
            {
                if(a[i][j]){
                    addEdge(i,j+n,1);
                    addEdge(j+n,i,0);
                }
            }
        }
        int mat=0,flow=0;
        memset(vis,false,sizeof vis);
        while(flow=dfs(s,inf)){
            mat+=flow;
            memset(vis,false,sizeof vis);
        }
        printf("%d\n", n-mat);
    }
    return 0;
}ICPC2017 Naning - The Maximum Unreachable Node Set
标签:输出 NPU 相互 inpu return nal diff tar icpc
原文地址:https://www.cnblogs.com/sciorz/p/9021829.html