POJ3268

本文介绍了一种利用两次Dijkstra算法求解图中从指定起点到其他各点的最大距离的方法。通过先正常存储边权重,再将边权重倒置存储,分别计算最短路径,最终求得各点间的最大路径距离。

//将边倒转后存放在两个数组中使用两次Dijkstra算法
#include <iostream>
#include <string.h>  //memset的头文件
using namespace std;
#define arraysize 1001
int maxData = 0x7fffffff; //最大整数
int dis[arraysize][arraysize]; 
int revdis[arraysize][arraysize];
bool final[arraysize];
int d[arraysize];
int revd[arraysize];
int N,M,X;
int sumDis[arraysize];
void Dij()
{
 memset(final,0,sizeof(final));
 memset(d,0,sizeof(d));
 for(int i=1;i<N+1;++i)
 {
  d[i] = dis[X][i];
 }
 final[X] = true;
 d[X] = 0;
 for(int i1=1;i1<N;++i1)
 {
  int min = maxData;
  int v = X;
  for(int i2=1;i2<N+1;++i2)
  {
   if(!final[i2] && min>d[i2])
   {
    min = d[i2];
    v = i2;
   }
  }
  final[v] = true;
  for(int i3=1;i3<N+1;++i3)
  {
   if(!final[i3] && dis[v][i3]<maxData)
   {
    if(d[v]+dis[v][i3]<d[i3])
    {
     d[i3] = d[v]+dis[v][i3];
    }
   }
  }
 }

 memset(final,0,sizeof(final));
 memset(revd,0,sizeof(revd));
 for(int i7=1;i7<N+1;++i7)
 {
  revd[i7] = revdis[X][i7];
 }
 final[X] = true;
 revd[X] = 0;
 for(int i4=1;i4<N;++i4)
 {
  int min = maxData;
  int v = X;
  for(int i5=1;i5<N+1;++i5)
  {
   if(!final[i5] && min>revd[i5])
   {
    min = revd[i5];
    v = i5;
   }
  }
  final[v] = true;
  for(int i6=1;i6<N+1;++i6)
  {
   if(!final[i6] && revdis[v][i6]<maxData)
   {
    if(revd[v]+revdis[v][i6]<revd[i6])
    {
     revd[i6] = revd[v]+revdis[v][i6];
    }
   }
  }
 }

 int tempmaxData = 0;
 for(int j=1;j<N+1;++j)
 {
  sumDis[j] = d[j]+revd[j];
  if(sumDis[j]>tempmaxData)
  {
   tempmaxData = sumDis[j];
  }
 }
 cout<<tempmaxData<<endl;
}
int main()
{
 //freopen("1.txt","r",stdin);
 while(cin>>N>>M>>X)
 {
  int start,end,weight;
  for(int i1=1;i1<N+1;++i1)
  {
   for(int i2=1;i2<N+1;++i2)
   {
    dis[i1][i2] = maxData;
    revdis[i1][i2] = maxData;
   }
  }
  for(int i=0;i<M;++i)
  {
   cin>>start>>end>>weight;
   dis[start][end] = weight;  //正常存储距离
   revdis[end][start] = weight; //将距离倒转后进行存储
  }
  Dij();
 }
 return 0;
}

转载于:https://www.cnblogs.com/north_dragon/archive/2010/04/25/1720691.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值