码迷,mamicode.com
首页 > 其他好文 > 详细

反向存边(逆图)

时间:2017-11-19 12:37:50      阅读:204      评论:0      收藏:0      [点我收藏+]

标签:memset   fine   git   inline   vector   ace   pac   return   har   

#include<iostream>
#include<cstdio>
#include<cstring>
#include<vector>
#include<queue>
using namespace std;
#define max1 1001
#define max2 100001
int n,m,dis[max1],sum=0;
vector<int>a[max1],b[max1],c[max1],d[max1];
queue<int>q;
bool pd[max1];
inline int read()
{
    int k=0,f=1;char c=getchar();
    for(;!isdigit(c);c=getchar())
      if(c==-) f=-1;
    for(;isdigit(c);c=getchar())
      k=k*10+c-0;
    return k*f;
}
void spfa1()
{
    memset(dis,127,sizeof(dis));
    memset(pd,0,sizeof(pd));
    q.push(1); pd[1]=1; dis[1]=0;
    while(!q.empty())
    {
        int now=q.front(); q.pop(); pd[now]=0;
        for(int i=0;i<a[now].size();i++)
        {
            int next=a[now][i];
            int l=b[now][i];
            if(dis[next]>dis[now]+l)
            {
                dis[next]=dis[now]+l;
                if(!pd[next])
                {
                    pd[next]=1;
                    q.push(next);
                }
            }
        }
    }
}
void spfa2()
{
    memset(dis,127,sizeof(dis));
    memset(pd,0,sizeof(pd));
    q.push(1); pd[1]=1; dis[1]=0;
    while(!q.empty())
    {
        int now=q.front(); q.pop(); pd[now]=0;
        for(int i=0;i<c[now].size();i++)
        {
            int next=c[now][i];
            int l=d[now][i];
            if(dis[next]>dis[now]+l)
            {
                dis[next]=dis[now]+l;
                if(!pd[next])
                {
                    pd[next]=1;
                    q.push(next);
                }
            }
        }
    }
}
int main()
{
    n=read(); m=read();
    for(int i=1;i<=m;i++)
    {
        int u,v,w;
        u=read(); v=read(); w=read();
        a[u].push_back(v); b[u].push_back(w);
        c[v].push_back(u); d[v].push_back(w);
    }
    spfa1();
    for(int i=2;i<=n;i++)
    sum+=dis[i];
    spfa2();
    for(int i=2;i<=n;i++)
    sum+=dis[i];
    cout<<sum;
    return 0;
}

洛谷 P1629 邮递员送信

一个邮递员要送东西,邮局在节点1.他总共要送N-1样东西,其目的地分别是2~N。由于这个城市的交通比较繁忙,因此所有的道路都是单行的,共有M条道路,通过每条道路需要一定的时间。这个邮递员每次只能带一样东西。求送完这N-1样东西并且最终回到邮局最少需要多少时间。

思路: 1.先求1到各个点的最短路

2.再求各个点到1的最短路(反向存边再求1到各个点的最短路,即为原图中各个点到1的最短路)

可用范围:1.有向图

2.多点到同一点的最短路

反向存边(逆图)

标签:memset   fine   git   inline   vector   ace   pac   return   har   

原文地址:http://www.cnblogs.com/std-legendary/p/7859206.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!