(tarjan+匈牙利算法) hdu 3861

F - The King’s Problem

Time Limit:1000MS     Memory Limit:32768KB     64bit IO Format:%I64d & %I64u

Submit Status Practice HDU 3861

Description

In the Kingdom of Silence, the king has a new problem. There are N cities in the kingdom and there are M directional roads between the cities. That means that if there is a road from u to v, you can only go from city u to city v, but can’t go from city v to city u. In order to rule his kingdom more effectively, the king want to divide his kingdom into several states, and each city must belong to exactly one state.What’s more, for each pair of city (u, v), if there is one way to go from u to v and go from v to u, (u, v) have to belong to a same state.And the king must insure that in each state we can ether go from u to v or go from v to u between every pair of cities (u, v) without passing any city which belongs to other state. 
  Now the king asks for your help, he wants to know the least number of states he have to divide the kingdom into.

Input

The first line contains a single integer T, the number of test cases. And then followed T cases.

The first line for each case contains two integers n, m(0 < n <= 5000,0 <= m <= 100000), the number of cities and roads in the kingdom. The next m lines each contains two integers u and v (1 <= u, v <= n), indicating that there is a road going from city u to city v.

Output

The output should contain T lines. For each test case you should just output an integer which is the least number of states the king have to divide into.

Sample Input

1
3 2
1 2
1 3

Sample Output

2

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<cstdlib>
#include<string>
#include<algorithm>
#include<vector>
#include<set>
#include<stack>
#include<queue>
#include<map>
using namespace std;
stack<int> s;
vector<int> e[50005],mp[50005];
int use[50005],Dfs[50005],low[50005];
int mark[50005],link[50005],isstack[50005];
int newflag,top;
int n,m;
struct node
{
    int x,y;
}nd[150005];
void init()
{
    memset(use,0,sizeof(use));
    memset(Dfs,0,sizeof(Dfs));
    memset(low,0,sizeof(low));
    memset(link,-1,sizeof(link));
    memset(isstack,0,sizeof(isstack));
    top=0;
    newflag=0;
    while(!s.empty()) s.pop();
    for(int i=1;i<=n;i++)
        e[i].clear(),mp[i].clear();
}
bool dfs(int x)
{
    for(int i=0;i<mp[x].size();i++)
    {
        int v=mp[x][i];
        if(mark[v]==-1)
        {
            mark[v]=1;
            if(link[v]==-1||dfs(link[v]))
            {
                link[v]=x;
                return true;
            }
        }
    }
    return false;
}
void tarjan(int u)
{
    Dfs[u]=low[u]=++top;
    isstack[u]=1;
    s.push(u);
    for(int i=0;i<e[u].size();i++)
    {
        int v=e[u][i];
        if(!Dfs[v])
        {
            tarjan(v);
            low[u]=min(low[u],low[v]);
        }
        else if(isstack[v])
        {
            low[u]=min(low[u],Dfs[v]);
        }
    }
    if(Dfs[u]==low[u])
    {
        newflag++;
        int x;
        do
        {
            x=s.top();
            s.pop();
            use[x]=newflag;
            isstack[x]=0;
        }while(x!=u);
    }
}

int main()
{
    int tt;
    scanf("%d",&tt);
    while(tt--)
    {
        init();
        scanf("%d%d",&n,&m);
        for(int i=0;i<m;i++)
        {
            scanf("%d%d",&nd[i].x,&nd[i].y);
            e[nd[i].x].push_back(nd[i].y);
        }
        for(int i=1;i<=n;i++)
        {
            if(!Dfs[i])
                tarjan(i);
        }
        for(int i=0;i<m;i++)
        {
            int x,y;
            x=use[nd[i].x],y=use[nd[i].y];
            if(x==y)
                continue;
            mp[x].push_back(y);
        }
        int ans=0;
        for(int i=1;i<=newflag;i++)
        {
            memset(mark,-1,sizeof(mark));
            if(dfs(i))
                ans++;
        }
        printf("%d\n",newflag-ans);
    }
    return 0;
}

  

时间: 2024-12-15 01:46:48

(tarjan+匈牙利算法) hdu 3861的相关文章

LCA(最近公共祖先)--tarjan离线算法 hdu 2586

HDU 2586 How far away ? Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 11320    Accepted Submission(s): 4119 Problem Description There are n houses in the village and some bidirectional roads c

(匈牙利算法) hdu 1281

棋盘游戏 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 2757    Accepted Submission(s): 1612 Problem Description 小希和Gardon在玩一个游戏:对一个N*M的棋盘,在格子里放尽量多的一些国际象棋里面的“车”,并且使得他们不能互相攻击,这当然很简单,但是Gardon限制了只有某些格

(二分+匈牙利算法) hdu 2236

无题II Time Limit: 2000/2000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 1198    Accepted Submission(s): 535 Problem Description 这是一个简单的游戏,在一个n*n的矩阵中,找n个数使得这n个数都在不同的行和列里并且要求这n个数中的最大值和最小值的差值最小. Input 输入一个整数T表示T组数据.对

(匈牙利算法) hdu 5093

Battle ships Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total Submission(s): 553    Accepted Submission(s): 223 Problem Description Dear contestant, now you are an excellent navy commander, who is responsible o

(匈牙利算法) hdu 2119

#include<iostream> #include<cstdio> #include<cstring> #include<string> #include<cmath> #include<algorithm> #include<cstdlib> using namespace std; int n,m,a[110][110],g[110][110],mark[110],link[110],ans; bool dfs(i

(匈牙利算法) hdu 4185

Oil Skimming Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 993    Accepted Submission(s): 422 Problem Description Thanks to a certain "green" resources company, there is a new profitable

(匈牙利算法) hdu 2063

过山车 Time Limit: 1000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 12125    Accepted Submission(s): 5302 Problem Description RPG girls今天和大家一起去游乐场玩,终于可以坐上梦寐以求的过山车了.可是,过山车的每一排只有两个座位,而且还有条不成文的规矩,就是每个女生必须找个个男生做par

HDU 2063:过山车(二分匹配,匈牙利算法)

过山车 Time Limit: 1000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 9745    Accepted Submission(s): 4294 Problem Description RPG girls今天和大家一起去游乐场玩,终于可以坐上梦寐以求的过山车了.可是,过山车的每一排只有两个座位,而且还有条不成文的规矩,就是每个女生必须找个个男生做par

HDU 1150:Machine Schedule(二分匹配,匈牙利算法)

Machine Schedule Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 5371    Accepted Submission(s): 2658 Problem Description As we all know, machine scheduling is a very classical problem in compu