zoukankan      html  css  js  c++  java
  • [題解]拓撲排序(優先隊列/字典序最小)

     考试抄书(日常)


    P2038 -- 小叶子的故事之写代码 

    时间限制:1000MS      内存限制:131072KB 

    题目描述(correct.cpp)

    小叶子要写一道砍手题,要写N个函数。小叶子作为一名强迫症患者,喜欢按从上到下的顺序写函数,他会在写代码之前给要写的函数排个顺序依次完成。现在小叶子给你M个关系如(x,y),表示函数y要调用函数x(即函数x要写在函数y之前)。假设小叶子不会使用函数声明,请你设计一个字典序最小的序列。如果没法得到这样一个序列,则输出“OMG.”(没有引号)

    输入格式(correct.in)

    第一行有两个整数N,M。

    接下来M行每行两个数x、y,表示x要写在y前面

    输出格式(correct.out)

    一行N个数,表示字典序最小的序列

    样例输入

    5 5

    1 2

    2 3

    1 3

    1 4

    4 5

    样例输出

    1 2 3 4 5

    数据规模与约定

    对于 40% 的数据,N,M <= 5,000。

    对于 100% 的数据,N,M <= 100,000。


     

    裸的拓撲排序,字典序最小<=>把隊列換成優先隊列

    #include<iostream>
    #include<cstdio>
    #include<queue>
    #include<algorithm>
    using namespace std;
    const int maxn=100010;
    int n,m;
    struct node{
        int v,nxt;
    }e[maxn*2];
    int head[maxn],cnt,tot;
    int in[maxn],a[maxn];
    void add(int u,int v){e[++cnt].v=v;e[cnt].nxt=head[u];head[u]=cnt;}
    void topo(){
        priority_queue<int,vector<int>,greater<int> >q;
        for(int i=1;i<=n;i++)
        if(in[i]==0)q.push(i);
        while(!q.empty()){
            int x=q.top();q.pop();
            a[++tot]=x;
            for(int i=head[x];i;i=e[i].nxt){
                int y=e[i].v;
                if(--in[y]==0)q.push(y);
            }
        }
    }
    int main()
    {
        scanf("%d%d",&n,&m);
        for(int i=1,x,y;i<=m;i++){
            scanf("%d%d",&x,&y);
            add(x,y);in[y]++;
        }
        topo();
        if(tot==n)
        for(int i=1;i<=tot;i++)
        printf("%d ",a[i]);
        else printf("OMG.");
    }
  • 相关阅读:
    笔记56 Mybatis快速入门(七)
    笔记55 Mybatis快速入门(六)
    笔记54 Mybatis快速入门(五)
    笔记53 Mybatis快速入门(四)
    笔记52 Mybatis快速入门(三)
    笔记51 Mybatis快速入门(二)
    笔记50 Mybatis快速入门(一)
    笔记49 在Spittr应用中整合Hibernate
    198. House Robber,213. House Robber II
    303. Range Sum Query
  • 原文地址:https://www.cnblogs.com/superminivan/p/10703079.html
Copyright © 2011-2022 走看看