cf - #346 E-New Reform

#include <iostream>
#include <vector>
using namespace std;
/****************************************************************************************************************
                题意:
                    给你一个图,现在要你给这个图里面的边定方向,使得入度为0的点最少。
                思路:
                    1, 对于一个连通块而言,如果里面存在一个环,那么必然所有点的入度都可以大于等于1
                        否则的话,就存在一个点的入度为0。
                    2,(判断连通块是否存在环)
                        假设当前的节点一个标号id,如果下一个要访问的节点未被访问过,
                        那么下一个访问的节点的标号是当前的id 1,
                        这里,我们先看看如果图没有环,那么会有一条路径从id开始一直往前,直到叶子节点,
                        最后一个叶子节点的标号可能是id x,那么假设的确有一个节点的标号为id x,
                        而且这个节点和id直接也相连,是否说明有环存在。除非x=1,因为如果x=1,
                        说明,实际上这个节点是和id节点直接连接的边。
                    3, 最后 dfs 一波就好了
****************************************************************************************************************/
const int maxn = 1e5+7;
vector <int> E[maxn];
int n,m,flag;
int vis[maxn];
void dfs(int x,int fa)
{
    if(vis[x]){
        flag = 1;
        return;
    }
    vis[x]=1;
    for(int i=0;i<E[x].size();i++){
        int v=E[x][i];
        if(v==fa)continue;
        dfs(v,x);
    }
}
int main()
{
    while(cin>>n>>m)
    {
        for(int i=1;i<=m;i++){
            int x,y;
            cin>>x>>y;
            E[x].push_back(y);
            E[y].push_back(x);
        }
        int ans = 0;
        for(int i=1;i<=n;i++){
            if(!vis[i]){
                flag = 0;
                dfs(i,-1);
                if(!flag)ans++;
            }
        }
        cout<<ans<<endl;
    }
    return 0;
}


posted on 2016-04-12 23:43  Jstyle  阅读(118)  评论(0编辑  收藏  举报

导航