• P1260 工程规划


    差分约束板子

    差分约束:把 i - j >= x 操作等价于从 j 到 i 连一条边权为 x 的边。然后跑一遍spfa统计最短路,即为一组合法序列。

    这道题里要求以一个点为基准点 0 ,在跑完spfa之后统计最小的dis值,然后按顺序输出dis值减去这个最小值即可。

    另一个问题是图不一定连通,有两个解决方法:

    1.建一个万能点与所有的点相连,当然边权都是0.

    2.跑spfa的时候要记录每个点的弹出次数,因此遍历一遍点,弹出次数为0就spfa,否则continue

    代码:

    #include<iostream>
    #include<cmath>
    #include<cstdio>
    #include<cstdlib>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    int n,m,h[2005]={},dis[2005]={},cnt=0,minn,que[1000500]={},times[2005]={},head,tail;
    bool vis[2005]={};
    struct Edge
    {
        int to,next,w;
    }e[10005];
    void add(int u,int v,int w)
    {
        e[++cnt]=(Edge){v,h[u],w};
        h[u]=cnt;
    }
    void spfa(int st)
    {
        head=0;
        tail=1;
        dis[st]=0;
        que[1]=st;
        times[st]++;
        while(head<tail)
        {
            int u=que[++head];
            vis[u]=0;
            for(int i=h[u];i+1;i=e[i].next)
            {
                int v=e[i].to;
                if(dis[v]>dis[u]+e[i].w)
                {
                    dis[v]=dis[u]+e[i].w;
                    if(!vis[v])
                    {
                        vis[v]=1;
                        times[v]++;
                        if(times[u]>=n) 
                        {
                            printf("NO SOLUTION
    ");
                            exit(0);
                        }
                        que[++tail]=v;
                    }
                }
            }
        }
        vis[st]=0;
    }
    int main()
    {
        memset(h,-1,sizeof(h));
        scanf("%d%d",&n,&m);
        for(int i=1;i<=m;i++)
        {
            int u,v,w;
            scanf("%d%d%d",&u,&v,&w);
            add(v,u,w);
        }
        for(int i=1;i<=n;i++)
            dis[i]=214748364;
        for(int i=1;i<=n;i++)
        {
            if(times[i]) 
                continue;
            spfa(i);
        }
            minn=999999999;
            for(int i=1;i<=n;i++) 
                minn=min(minn,dis[i]);
            for(int i=1;i<=n;i++)     
                printf("%d
    ",dis[i]-minn);
        return 0;
    }
  • 相关阅读:
    HTTP请求 GET POST 网络编程实现(转)
    较老版本 AFNetworking 使用心得
    优秀java开源项目与解决方案推荐与概论
    URL的格式scheme
    用MATLAB实现字符串分割
    matlab search path
    matlab中的字符串数组与函数调用
    全新重装win8.1系统后 配置开发及办公环境步骤
    html图片上下翻滚展示代码
    html目录树的操作
  • 原文地址:https://www.cnblogs.com/charlesss/p/10534168.html
Copyright © 2020-2023  润新知