zoukankan      html  css  js  c++  java
  • airline

    题目描述

    A 国有 n 个城市从 1 到 n 编号,在城市间有 m 条单向航线。 A 国首都位于编号为 w 的城市,现在 A 国政府希望在首都召开会 议,就想要让各地人民都能够通过若干条航线到达首都,那么至少需 要新建多少条航线?(可能有重边和自环)

    输入输出格式

    输入格式:

    第一行三个整数 n,m,w 接下来 m 行,每行两个整数 xi,yi,表示存在一条从 xi 到 yi 城市 的单向航线

    输出格式:

    一个整数表示最小需要新建多少条航线

    输入输出样例

    输入样例#1: 复制
    5 4 1
    2 1
    1 2
    2 3
    3 4
    输出样例#1: 复制
    2

    说明

    对于 20%的数据 n<=10 m<=10 对于 40%的数据 n<=100 m<=100 对于 100%的数据 n<=10^6 m<=10^6

    老师出的毒瘤题

    本来想让我们写tarjin,结果没人写(没人会写)

    题目给有向图,先反着建图,反着扫把能直接到终点的点标记

    然后正这扫,一个点正反都没扫,就进深搜,只扫着个点连着的一个点(我也只记录了一个点),一直扫下去,如果扫到以前扫过的点,答案数就不用+1了,不然答案数+1

    扫的过程中的点都标记为扫过

    为什么只扫一个

    1.扫的这个点能到终点或以前把他和终点建过边,高兴地返回

    2。扫的这个天目前还不能到终点,那就标记为能到终点,答案加一,虽然按最开始扫的点不是最优解,但全局上不变,你以后肯定还得连

    #include<bits/stdc++.h>

    using namespace std;

    int n,m,s,x,y,ans,a[1000001];

    vector<int>f[1000001];

    bool sao[1000001],zou[1000001];

    queue<int>q;

    void spfa()

    {

             q.push(s);

             sao[s]=1;

             while(q.empty()==0)

             {

                       int u=q.front();q.pop();

                       for(int i=0;i<f[u].size();i++)

                       {

                                int w=f[u][i];

                                if(sao[w]==0)

                                {

                                         sao[w]=1;

                                         q.push(w);

                                }

                       }

             }

    }

    bool dfs(int k)

    {

             if(a[k]==0)

             {

                       return 0;

             }

             if(zou[a[k]]==0)

             {

                       zou[a[k]]=1;

                       dfs(a[k]);

             }

             else

             return 1;

    }

    int main()

    {

             cin>>n>>m>>s;

             for(int i=0;i<m;i++)

             {

                       scanf("%d%d",&x,&y);

                       if(x!=y)

                       {

                                f[y].push_back(x);

                                a[x]=y;

                       }

             }

             spfa();

             for(int i=1;i<=n;i++)

             {

                       if(sao[i]==0&&zou[i]==0)

                       {

                                zou[i]=1;

                                if(dfs(i)==0)

                                {

                                         ans++;

                                }

                       }

             }

             cout<<ans;

    }

  • 相关阅读:
    日志处理
    md5加密
    os 模块
    time模块
    函数的进阶
    参数 返回值
    文件操作
    集合 拷贝
    linux如何更快的远程拷贝?scp,tar,rsync?
    修改内核临时端口范围
  • 原文地址:https://www.cnblogs.com/fanhao050109/p/11234962.html
Copyright © 2011-2022 走看看