zoukankan      html  css  js  c++  java
  • P4568 [JLOI2011]飞行路线(分层图)

    机房dalao推荐写的。。。(标签分层图)

    经过前几题的分层图的洗礼,我深刻地体会到了分层图的优点和好处(主要是不想打dp....)

    先说题吧....

    很明确,模型是最短路,但是,怎么跑k个,是个问题....

    解题过程:

    1、先跑最短路,记录路径,然后找路径上的k条最长边,删掉

    tips:贪心,很容易hack掉。

    2、建两层的分层图(以前打的都是两层居多)

    tips:会跑出0来....

    solution:

     主要就是:怎么连边喽....一开始老是卡住

    连边有2种情况:

    1. 同一层之间的边,边权为题目给的边权,同层之间连
    2. 层与层之间,一个点连到下一层的它对应的出点,边权为0,为单向边

    一共K层,上层可以跑到下层的出点,却不能回去,这就是一次免票。

    然后跑最短路,最后查t+n*k那个点的dis就可以了。

    for(int i=1;i<=m;i++)
        {
            int x,y,z;
            x=read();y=read();z=read();
            addedge(x,y,z);
            addedge(y,x,z);
            for(int j=1;j<=k;j++)
            {
                addedge(x+n*j,y+n*j,z);
                addedge(y+n*j,x+n*j,z);
                addedge(x+(j-1)*n,y+j*n,0);
                addedge(y+(j-1)*n,x+j*n,0);
            }
        }

    如上,分层连边。

    之后就是一个spfa的事了(然而我各种常数(畜生)优化+O2卡到比旁边dalao快600ms的地步哈哈哈哈)

    值得注意:

    1、最后要把每一层的t点连在一起,因为如果在第二层就跑到了最短,在最后一层的t并不能查到正确答案

    2、一共有k+1层,所以初始化dis要k+1层,因为这个卡了一小会...

    #include<bits/stdc++.h>
    using namespace std;
    const int maxn=6e6+10;
    int n,m,k;
    int s,t;
    inline int read()
    {
        int x=0,f=1;char s=getchar();
        while(s>'9'||s<'0'){if(s=='-')f=-1;s=getchar();}
        while(s<='9'&&s>='0'){x=x*10+s-'0';s=getchar();}
        return x*f;
    }
    struct edge
    {
        int to,next,dis;
    }e[maxn];
    int head[maxn],cnt;
    inline void addedge(int from,int to,int dis)
    {
        e[++cnt].next=head[from];
        e[cnt].to=to;
        e[cnt].dis=dis;
        head[from]=cnt;
    }
    int dis[maxn],vis[maxn];
    struct cmp
    {
        bool operator () (int a,int b)
        {
            return dis[a]>dis[b];
        }
    };
    priority_queue < int , vector < int > , cmp > q;
    //queue < int > q;
    void spfa(int s)
    {
    
        for(int i=0;i<=(k+1)*n;i++)
        {
            dis[i]=2147483647;
            vis[i]=0;
        }
        //memset(dis,0x3f,sizeof(dis));
        q.push(s);
        dis[s]=0;
        vis[s]=1;
        while(!q.empty())
        {
            //cout<<233;
            int u=q.top();
            //int u=q.front();
            q.pop();
            vis[u]=0;
            for(int i=head[u];i;i=e[i].next)
            {
                int v=e[i].to;
                if(dis[v]>dis[u]+e[i].dis)
                {
                    dis[v]=dis[u]+e[i].dis;
                    if(vis[v]==0)
                    {
                        q.push(v);
                        vis[v]=1;
                    }
                }
            }
        }
    }
    int main()
    {
        n=read();
        m=read();
        k=read();
        s=read();
        t=read();
        for(int i=1;i<=m;i++)
        {
            int x,y,z;
            x=read();
            y=read();
            z=read();
            addedge(x,y,z);
            addedge(y,x,z);
            for(int j=1;j<=k;j++)
            {
                addedge(x+n*j,y+n*j,z);
                addedge(y+n*j,x+n*j,z);
                addedge(x+(j-1)*n,y+j*n,0);
                addedge(y+(j-1)*n,x+j*n,0);
            }
        }
        for(int i=1;i<=k;i++)
        addedge(t+(i-1)*n,t+i*n,0);
        spfa(s);
        cout<<dis[t+k*n];//printf("%d",dis[t+k*n]);
        return 0;
    }

    现在来说一说dp和分层图的关系:

    首先,分层图的“层”是什么,它就是dp中的状态。在一些图论题目中,状态不好转移,就可以使用分层图进行转移,不需要再管“从哪转移”这个问题,剩下的最优解直接交给spfa就行了。(最优贸易

    这些状态之间可以互相转移,一般在二维或是以上,可以省去一些不相关状态的枚举,但是因为spfa的广泛枚举性还是会枚举更多“不是最优解”的状态的。

    (完)

     

  • 相关阅读:
    MSDN Magazine搞错了
    Visual Studio 2005中设置调试符号(Debug Symbols)
    BCB 6的问题
    吴裕雄天生自然Spring Boot使用Spring Data JPA实现人与身份证的一对一关系映射
    吴裕雄天生自然Spring BootSpring Data JPA
    吴裕雄天生自然Spring BootSpring Boot对JSP的支持
    吴裕雄天生自然Spring BootSpring Boot的异常统一处理
    吴裕雄天生自然Spring Boot使用Spring Data JPA实现Author与Article的一对多关系映射
    吴裕雄天生自然Spring Boot解决 Error creating bean with name 'entityManagerFactory' defined in class path resource
    吴裕雄天生自然Spring Boot@ExceptionHandler注解和@ControllerAdvice注解
  • 原文地址:https://www.cnblogs.com/ajmddzp/p/11503135.html
Copyright © 2011-2022 走看看