lougu3906 Geodetic

分析

求任意两点间的最短路,容易想到是Floyd,怎么存中间路径,直接用longlong压缩存就好

注意相同长度的路径要更新路径

代码

 1 /********************
 2 User:Mandy.H.Y
 3 Language:c++
 4 Problem:luogu3906
 5 ********************/
 6 
 7 #include<bits/stdc++.h>
 8 
 9 using namespace std;
10 
11 const int maxn = 45;
12 
13 int n,m;
14 int g[maxn][maxn];
15 long long a[maxn][maxn];
16 
17 template<class T>inline void read(T &x){
18     x = 0;bool flag = 0;char ch = getchar();
19     while(!isdigit(ch)) flag |= ch == '-',ch = getchar();
20     while(isdigit(ch)) x = (x << 1) + (x << 3) + (ch ^ 48),ch = getchar();
21     if(flag) x = -x;
22 }
23 
24 template<class T>void putch(const T x){
25     if(x > 9) putch(x / 10);
26     putchar(x % 10 | 48);
27 }
28 
29 template<class T>void put(const T x){
30     if(x < 0) putchar('-'),putch(-x);
31     else putch(x);
32 }
33 
34 void file(){
35     freopen("3906.in","r",stdin);
36     freopen("3906.out","w",stdout);
37 }
38 
39 void readdata(){
40     read(n);read(m);
41     memset(g,0x3f3f3f3f,sizeof(g));
42     for(int i = 1;i <= m; ++ i){
43         int u,v;
44         read(u);read(v);
45         g[u][v] = g[v][u] = 1;
46     }
47     for(int i = 1;i <= n; ++ i) g[i][i] = 0;
48 }
49 
50 void Floyd(){
51     for(int k = 1; k <= n; ++ k){
52         for(int i = 1;i <= n; ++ i){
53             for(int j = 1;j <= n; ++ j){
54                 if(g[i][k] + g[k][j] < g[i][j]){
55                     a[i][j] = (a[i][k] | a[k][j]) | (1LL << k);
56                     a[j][i] = a[i][j];
57                     g[i][j] = g[i][k] + g[k][j];
58                     g[j][i] = g[i][j];
59                 } else if(g[i][k] + g[k][j] == g[i][j]){
60                     a[i][j] |= ((a[i][k] | a[k][j]) | (1LL << k));
61                     a[j][i] = a[i][j];
62                 }
63             }
64         }
65     }
66 }
67 
68 void work(){
69     
70     Floyd();
71     int k;read(k);
72     
73     for(int i = 1;i <= k; ++ i){
74         int u,v;
75         read(u);read(v);
76         a[u][v] = a[u][v] | (1LL << u) | (1LL << v);
77         for(int i = 1;i <= n; ++ i){
78             if((1LL << i) & a[u][v]){
79                 put(i);
80                 putchar(' ');
81             }
82         }
83         puts("");
84     }
85     
86 }
87 
88 int main(){
89 //    file();
90     readdata();
91     work();
92     return 0;
93 }
View Code
非做顽石不可,哪管他敬仰暗唾
原文地址:https://www.cnblogs.com/Mandy-H-Y/p/11449107.html