Cow Relays POJ - 3613 (floyd+快速幂)

For their physical fitness program, N (2 ≤ N ≤ 1,000,000) cows have decided to run a relay race using the T (2 ≤ T ≤ 100) cow trails throughout the pasture.

Each trail connects two different intersections (1 ≤ I1i ≤ 1,000; 1 ≤ I2i ≤ 1,000), each of which is the termination for at least two trails. The cows know the lengthi of each trail (1 ≤ lengthi  ≤ 1,000), the two intersections the trail connects, and they know that no two intersections are directly connected by two different trails. The trails form a structure known mathematically as a graph.

To run the relay, the N cows position themselves at various intersections (some intersections might have more than one cow). They must position themselves properly so that they can hand off the baton cow-by-cow and end up at the proper finishing place.

Write a program to help position the cows. Find the shortest path that connects the starting intersection (S) and the ending intersection (E) and traverses exactly N cow trails.

Input

* Line 1: Four space-separated integers: N, T, S, and E
* Lines 2..T+1: Line i+1 describes trail i with three space-separated integers: lengthi , I1i , and I2i

Output

* Line 1: A single integer that is the shortest distance from intersection S to intersection E that traverses exactly N cow trails.

Sample Input

2 6 6 4
11 4 6
4 4 8
8 4 9
6 6 8
2 6 9
3 8 9

Sample Output

10


题意:求过s,t两点的刚好经过k条边的最短路
思路:任意最短路可以想到Floyd,(01矩阵的乘积A^k中,A[i][j]代表刚好经过k条边的从i到j的数量)
maps【i】【j】 为 经过一条边的最短路, 对于maps【i】【k】 + maps【k】【j】 可以看出是经过两条边的最短路
那么对于
r+m == k 且 A为经过r条边的最短路,B为经过m条边的最短路,通过maps【i】【k】+maps【k】【j】就得到了刚好经过k条边的最短路

 1 #include<cstdio>
 2 #include<iostream>
 3 #include<cstring>
 4 using namespace std;
 5 
 6 int n,k,m,s,t;
 7 int has[1005];
 8 struct matrix
 9 {
10     int maps[205][205];
11     matrix operator *(const matrix &x)const
12     {
13         matrix c;
14         memset(c.maps,0x3f,sizeof(c.maps));
15         for(int k=1;k<=n;k++)
16         {
17             for(int i=1;i<=n;i++)
18             {
19                 for(int j=1;j<=n;j++)
20                 {
21                     c.maps[i][j] = min(c.maps[i][j],maps[i][k]+x.maps[k][j]);
22                 }
23             }
24         }
25         return c;
26     }
27 };
28 
29 matrix qpow(matrix a,int k)
30 {
31     matrix ans = a;
32     k--;
33     while(k)
34     {
35         if(k&1)ans = ans * a;
36         a = a*a;
37         k >>= 1;
38     }
39     return ans;
40 }
41 int main()
42 {
43     while(~scanf("%d%d%d%d",&k,&m,&s,&t))
44     {
45         int tot=0;
46         matrix ans;
47         memset(ans.maps,0x3f,sizeof(ans.maps));
48         for(int i=1;i<=m;i++)
49         {
50             int w,x,y;
51             scanf("%d%d%d",&w,&x,&y);
52             if(!has[x])
53             {
54                 has[x] = ++tot;
55             }
56             if(!has[y])
57             {
58                 has[y] = ++tot;
59             }
60             if(w < ans.maps[has[x]][has[y]])
61             {
62                 ans.maps[has[x]][has[y]] = ans.maps[has[y]][has[x]] = w;
63             }
64         }
65         n = tot;
66         ans = qpow(ans,k);
67         printf("%d\n",ans.maps[has[s]][has[t]]);
68     }
69 }
View Code

猜你喜欢

转载自www.cnblogs.com/iwannabe/p/10680779.html