这是一题求多点路线问题,每两个点之间都可能存在关系,可以用dfs,不过如果有环的话就会爆栈,也可以有floy直接暴搜。关键在于浮点型计算的时候回丢精度,可以每次都不做浮点型的乘除法,最后在运算。不过这题在取整的时候为啥要减一个精度,还是不太明白。
double类型的精度只能达到小数点后16位,大于16位就不能比较大小了。所以浮点型还是慎用。
代码:
#include <iostream> #include <cstring> #include <cstdio> #include <cmath> #include <string> #include <algorithm> #include <vector> #include <queue> #include <map> #include <set> #define INF 1000000005 #define ep 1e-8 using namespace std; map<string,int> q; string q2[33]; double d[33][33]; void floy(int n) { for(int k=0;k<n;k++) { for(int i=0;i<n;i++) { for(int j=0;j<n;j++) { if(d[i][k]!=INF&&d[k][j]!=INF&&i!=j&&k!=i&&k!=j) { d[i][j]=d[i][k]*d[k][j]; } } } } } void init() { for(int i=0;i<33;i++) { d[i][i]=1; for(int j=0;j<33;j++) { if(i!=j) d[i][j]=INF; } } q.clear(); } int main() { int n,tt=1; while(scanf("%d",&n)==1) { if(!n) break; init(); int p=0; for(int i=0;i<n;i++) { int a,b; string sa,sb; int ia,ib; char sc[10]; scanf("%d",&a);cin>>sa; if(q.count(sa)==0) { q[sa]=p++; } ia=q[sa]; q2[ia]=sa; scanf("%s",sc); scanf("%d",&b); cin>>sb; if(q.count(sb)==0) { q[sb]=p++; } ib=q[sb]; q2[ib]=sb; d[ia][ib]=(double)b/(double)a; d[ib][ia]=(double)a/(double)b; } double num; string s; scanf("%lf",&num); cin>>s; int id=q[s]; floy(p); double eps=INF; int ansnum; string ansname; for(int i=0;i<p;i++) { if(d[id][i]!=INF&&id!=i) { int tmpnum=(int)ceil(num*d[id][i]-ep);//这里要保留精度取整 if(tmpnum>100000) continue;//这里没看到 double tmpeps=(double)tmpnum*d[i][id]; if(tmpeps<eps) { eps=tmpeps; ansnum=tmpnum; ansname=q2[i]; } } } printf("Case %d: %d ",tt++,ansnum); cout<<ansname<<endl; } return 0; }