5. Shortestpath in multistage graphs. Find the shortest path from 0 to 15 for the followinggraph.
A multistagegraph is a graph (1) G=(V,E) with V partitioned into K>= 2 disjoint subsets such that if (a,b) is in E,then a is in Vi , and b is in Vi+1 for somesubsets in the partition; and (2) | V1 | = |VK | = 1.
方法一:
#include <iostream>
#include <vector>
#include <iomanip>
using namespace std;
#define INF 0x1f1f1f1f
int dest[16][16];
int value[16][16];
void Floyed(int dest[][16])
{
for(int k=0;k<16; k++)
for(int i=0; i<16; i++)
for(int j=0; j<16; j++)
{
if(i!=j&&j!=k&&i!=k)
{
if(dest[i][j]>dest[i][k]+dest[k][j])
{
dest[i][j] = dest[i][k]+dest[k][j];
value[i][j] = k;
}
}
}
}
void print(int t)
{
if(value[0][t] == 0)
return;
cout<< value[0][t]<< " ";
print(value[0][t]);
}
int main()
{
int v, u,e;
cin>> v >>u >> e;
memset(dest,INF, sizeof(dest));
while(!(v==0 && u == 0&& e == 0))
{
dest[v][u] = e;
cin >> v>> u >>e;
}
Floyed(dest);
cout<< dest[0][15]<< endl;
for(int i =0; i < 16; i++)
{
for(int j = 0; j < 16; j++)
{
cout << value[i][j]<< " ";
}
cout << endl;
}
cout<< "经过的点分别是:"<<endl;
print(15);
system("pause");
return0;
}
方法二:
使用递归的dp。
#include <iostream>
using namespace std;
#define inf 1<<20
int n,a[16][16],d[16];
int dp(int i)
{
if(i ==15)
return d[i]=0;
if(d[i] !=0)
return d[i];
int min =9999999, t;
for(int j =0; j <= 15; j++)
if(a[i][j] != 0 && i != j)
{
t = dp(j) + a[i][j];
if(t < min)
min=t;
}
return d[i] = min;
}
int main()
{
int v, u, e;
cin >> v>> u >>e;
while(!(v == 0 && u == 0&& e == 0))
{
a[v][u] = e;
cin >> v>> u >>e;
}
memset(d, 0,sizeof(d));
cout<< dp(0)<< endl;//1到n-1个矩阵 矩阵i的左右为 i-1,i
for(int i =0; i < 16; i++)
cout << d[i]<< " ";
system("pause");
return0;
}
方法三:
使用Dijstra算法。
Dijkstra算法的时间效率依赖于用来实现优先队列的数据结构以及用来表示输入图本身的数据结构,如果图用权重矩阵表示,优先队列用无序数组来实现,该算法属于O(|V|*|V|).如果图用邻接链表表示,优先队列用最小堆来实现,该算法属于O(|E|log|v|).如果用一种斐波那契堆的更复杂的数据结构来实现优先队列,它的最差效率会更好一些。