题目描述
繁繁想和小伙伴们打游戏,游戏在一个山庄进行,这个山庄有N座山,编号为1到N,为了方便大家在不同的山之间移动,繁繁建了一些桥,由于技术的原因,桥连接的两座山的高度差不能超过d,现在已知这些桥,求这个山庄最高的山和最低的山差距最大是多少?数据保证所有山之间都是联通的。
输入
第一个一个数T,表示测试数据数量(T<=5,2<=N<=50,0<=d<=1000)
每组数据第一行两个数N和d
接下来一个N行N列的矩阵,第i行j列为Y表示i和j之间建了一座桥,否则表示没有建保证第i行j列和第j行i列值相同,并且第i行第i列值为N
输出
T行,每行一个答案,若最大值可能为正无穷,输出-1
样例输入
3 3 10 NYN YNY NYN 2 1 NN NN 6 1000 NNYNNN NNYNNN YYNYNN NNYNYY NNNYNN NNNYNN
样例输出
20 -1 3000
提示
第一个样例,1和2之间不能超过d,2和3之间不能超过d,那么最大就是1和2差恰好为d,2和3差恰好为d
对于20%的数据,T<=3,N<=40
对于50%的数据,T<=3
对于100%的数据,T<=5,2<=N<=50,0<=d<=1000
代码
//#pragma GCC optimize(3) #include<iostream> #include<cstdio> #include<algorithm> #include<cstring> #include<cmath> #include<climits> #include<queue> #include<set> #define max(x,y) ((x)>(y)?(x):(y)) #define min(x,y) ((x)<(y)?(x):(y)) #define swap(x,y) (x^=y,y^=x,x^=y) typedef long long ll; using namespace std; template<typename T>inline void read(T &x) { x=0; T f=1; char c=getchar(); for(; c<'0'||c>'9'; c=getchar()) if(c=='-') f=-1; for(; c>='0'&&c<='9'; c=getchar()) x=(x<<1)+(x<<3)+(c&15); } template<typename T>inline void print(T x) { if(x<0) putchar('-'),x*=-1; if(x>=10) print(x/10); putchar(x%10+'0'); } const int N=55; const int INF=0x3f3f3f3f; int num[N][N]; int n,d; int main() { int t; read(t); char ch; while(t--) { memset(num,0x3f,sizeof(num)); read(n); read(d); for(int i=1; i<=n; i++) for(int j=1; j<=n; j++) { cin>>ch; if(ch=='Y') num[i][j]=num[j][i]=1; } for(int k=1; k<=n; k++) for(int i=1; i<=n; i++) for(int j=1; j<=n; j++) { num[i][j]=min(num[i][j],num[i][k]+num[k][j]); } int ans=0; for(int i=1; i<=n; i++) for(int j=i+1; j<=n; j++) ans=max(ans,num[i][j]); if(ans==INF) cout<<-1<<endl; else { print(ans*d); puts(""); } } return 0; }
思路
所以最短路的最大值。
PS
最短路是基于dp思想的,注意模板,以下这种dp不可取。
贴一个错误的代码
//#pragma GCC optimize(3) #include<iostream> #include<cstdio> #include<algorithm> #include<cstring> #include<cmath> #include<climits> #include<queue> #include<set> #define max(x,y) ((x)>(y)?(x):(y)) #define min(x,y) ((x)<(y)?(x):(y)) #define swap(x,y) (x^=y,y^=x,x^=y) typedef long long ll; using namespace std; template<typename T>inline void read(T &x) { x=0; T f=1; char c=getchar(); for(; c<'0'||c>'9'; c=getchar()) if(c=='-') f=-1; for(; c>='0'&&c<='9'; c=getchar()) x=(x<<1)+(x<<3)+(c&15); } template<typename T>inline void print(T x) { if(x<0) putchar('-'),x*=-1; if(x>=10) print(x/10); putchar(x%10+'0'); } const int N=55; int num[N][N]; int n,d; ll dp[N]; int main() { int t; read(t); while(t--){ memset(dp,0,sizeof(dp)); memset(num,0,sizeof(num)); char ch; read(n); read(d); for(int i=1;i<=n;i++) for(int j=1;j<=n;j++) { cin>>ch; if(ch=='Y') { num[i][j]=num[j][i]=1; } } for(int i=1;i<=n;i++) for(int j=1;j<i;j++) { if(i!=j&&num[i][j]) { dp[i]=max(dp[i],dp[j]+d); } } ll ans=0; for(int i=1;i<=n;i++) ans=max(ans,dp[i]); if(ans==0) cout<<-1<<endl; else cout<<ans<<endl; } return 0; }