• 简单tarjan》一道裸题(BZOJ1051)(easy)


    这是一道水题,实际考察的是你会不会写强连通分量。。。(在BZOJ上又水了一道题)

    Description

      每一头牛的愿望就是变成一头最受欢迎的牛。现在有N头牛,给你M对整数(A,B),表示牛A认为牛B受欢迎。 这
    种关系是具有传递性的,如果A认为B受欢迎,B认为C受欢迎,那么牛A也认为牛C受欢迎。你的任务是求出有多少头
    牛被所有的牛认为是受欢迎的。

    Input

      第一行两个数N,M。 接下来M行,每行两个数A,B,意思是A认为B是受欢迎的(给出的信息有可能重复,即有可
    能出现多个A,B)

    Output

      一个数,即有多少头牛被所有的牛认为是受欢迎的。

    Sample Input

    3 3
    1 2
    2 1
    2 3

    Sample Output

    1

    HINT

    100%的数据N<=10000,M<=50000
     
    思路:直接强连通分量缩点,然后,因为题目没有告诉你  当没有一头牛受欢迎时  应该输出什么,所以我们认为题目一定有解,所以直接tarjan就好啦
    强行给出代码
     1 #include<stdio.h>
     2 #include<string.h>
     3 int head[11000],F[11000],w[11000],ass,stack[11000],n,point,m,D[11000],ans;
     4 int min(int x,int y)
     5 {
     6     return x>y?y:x;
     7 }
     8 bool f[11000];
     9 struct shit{
    10     int aim,next,from;
    11 }e[51000];
    12 int T,time[51000],dfn[51000];
    13 void tarjan(int x)
    14 {
    15     time[x]=dfn[x]=++T;
    16     f[x]=true;
    17     stack[++ass]=x;
    18     for(int k=head[x];k;k=e[k].next)
    19     {
    20         int v=e[k].aim;
    21         if(!time[v])
    22         {
    23             tarjan(v);
    24             dfn[x]=min(dfn[x],dfn[v]);
    25         }
    26         else if(f[e[k].aim])dfn[x]=min(dfn[x],time[v]);
    27     }
    28     if(dfn[x]==time[x])
    29     {
    30         f[x]=false;
    31         while(stack[ass]!=x)
    32         {
    33             w[x]++;
    34             F[stack[ass]]=x;
    35             f[stack[ass--]]=false;
    36         }
    37         ass--;
    38     }
    39 }
    40 void fuck(int x,int y)
    41 {
    42     e[++point].aim=y;
    43     e[point].from=x;
    44     e[point].next=head[x];
    45     head[x]=point;
    46 }
    47 int main()
    48 {
    49     int a,b;
    50     scanf("%d%d",&n,&m);
    51     for(int i=1;i<=m;++i)
    52     {
    53         scanf("%d%d",&a,&b);
    54         fuck(a,b);
    55     }
    56     for(int i=1;i<=n;++i)F[i]=i,w[i]=1;
    57     for(int i=1;i<=n;++i)
    58     if(!time[i])tarjan(i);
    59     memset(head,0,sizeof(head));
    60     point=0;
    61     for(int i=1;i<=m;++i)
    62     {
    63         if(F[e[i].from]==F[e[i].aim])continue;
    64         else {
    65             D[F[e[i].from]]++;
    66             fuck(F[e[i].aim],F[e[i].from]);
    67         }
    68     }
    69     for(int i=1;i<=n;i++)
    70         if(F[i]==i&&!D[i])ans+=w[i];
    71     printf("%d",ans);
    72     return 0;
    73 }
    View Code

    没什么好PS的

  • 相关阅读:
    Hibernate(十三)迫切内连接fetch
    SQL多表联合查询(交叉连接,内连接,外连接)
    Hibernate入门(十二)离线条件检索
    Java基础IO流(二)字节流小案例
    Java基础IO流(一)
    Hibernate入门(十一)多对多案例
    mysql下载安装及常见问题
    数据库表数据恢复
    linux的自有(内置)服务
    linux下的别名机制
  • 原文地址:https://www.cnblogs.com/PencilWang/p/5914366.html
Copyright © 2020-2023  润新知