由于Floyd-Warshall算法采用了DP,所以这道题被大家一致归类为DP的问题。
这里题目的翻译。需要注意的是输入,如:
3
2 2 4 3 5
2 1 2 3 6
2 1 2 2 2
表示3个点的图,接下来每一行的行号代表一个点,如第一行 2 2 4 3 5 表示编号为 1(行号)的点出去有 2(第一个数字)条边,分别为指向2号边且长度为4,指向3号边且长度为5。再如:
5
3 4 4 2 8 5 3
1 5 8
4 1 6 4 10 2 7 5 2
0
2 2 5 1 5
这里倒数第2行为0,说明编号为4(行号)的点没有从自己出去的边。
另外如果不是连通图,输出“disjoint”。
最显然的两点间最短路径问题,Floyd-Warshall 算法时间复杂度o(n^3)。交上去0MS过的,可能是OJ的测试数据不是很大。找出任意两点间最短距离后,如果存在某点 i 和某点 j, i 到 j 和 j 到 i 的距离都是无穷大,则是非连通图。再扫描全部点,这点到其他点的距离中最长的,就是从这点出发点最少时间sum;所有点扫完后,所有sum中的最短时间则是所求。我的代码如下:
1: #include <iostream>
2: #include <cstdlib>
3: using namespace std;
4: const int MAX_INT = (1<<15);
5:
6: class Stockbrokers
7: {
8: public:
9: Stockbrokers(int** graph, const int vSize);
10: ~Stockbrokers();
11: void floyd();
12: void getMinTime();
13: private:
14: int** g;
15: int size;
16: };
17:
18: Stockbrokers::Stockbrokers(int** graph, const int vSize)
19: {
20: size = vSize;
21: if (size==0)
22: exit(-1);
23: g = graph;
24: }
25: Stockbrokers::~Stockbrokers()
26: {
27:
28: }
29: void Stockbrokers::floyd()
30: {
31: for (int k=1; k<size; k++)
32: {
33: for (int i=1; i<size; i++)
34: {
35: for (int j=1; j<size; j++)
36: {
37: if (g[i][k]>=MAX_INT || g[k][j]>=MAX_INT)
38: continue;
39: int temp = g[i][k] + g[k][j];
40: g[i][j] = g[i][j]<temp ? g[i][j] : temp;
41: }
42: }
43: }
44: }
45:
46: void Stockbrokers::getMinTime()
47: {
48: int minTime = MAX_INT, pos=1;
49: for (int from=1; from<size; from++)
50: {
51: int sum=0;
52: for (int to=1; to<size; to++)
53: {
54: if (g[from][to]>=MAX_INT)
55: {
56: sum = MAX_INT;
57: if (g[to][from]>=MAX_INT)
58: {
59: cout << "disjoint" << endl;
60: return;
61: }
62: break;
63: }
64: if (sum<g[from][to])
65: {
66: sum = g[from][to];
67: }
68: }
69: if (minTime>sum)
70: {
71: minTime = sum;
72: pos = from;
73: }
74: }
75: cout << pos << ' ' << minTime << endl;
76: }
77:
78: int main()
79: {
80: int size=0;
81: while(cin>>size && size!=0)
82: {
83: size++;
84: int** graph;
85: graph = new int*[size];
86: graph[0] = new int[size*size];
87: for (int i=1; i<size; i++)
88: {
89: graph[i] = graph[i-1] + size;
90: }
91: for (int i=1; i<size; i++)
92: {
93: for (int j=1; j<size; j++)
94: {
95: if (i==j) graph[i][j] = 0;
96: else graph[i][j] = MAX_INT;
97: }
98:
99: int pair=0;
100: cin >> pair;
101: while(pair--)
102: {
103: int vertex, val;
104: cin >> vertex >> val;
105: if (vertex>=size || (val<1 || val>10))
106: exit(-1);
107: else
108: graph[i][vertex] = val;
109: }
110: }
111:
112: Stockbrokers s(graph, size);
113: s.floyd();
114: s.getMinTime();
115:
116: delete[] graph[0];
117: delete[] graph;
118: }
119: return 0;
120: }