// Airlines (route) // PC/ultraviolet A IDs: 111208/10075, popularity: C, success rate: high level: 3 // verdict: accepted // submission date: 2011-11-01 // UV Run Time: 0.060 S // copyright (c) 2011, Qiu. Metaphysis # Yeah dot net // [solution] // This question combines the distance between two points on the spherical surface and the shortest path between each pair of nodes in the weighted graph. // The first key to this question is to calculate the distance between two points on the spherical surface, while there is a fixed formula for calculating the distance between two points on the spherical surface, which is very convenient. After finding the distance to the surface, you can use the Floyd-warshall algorithm to calculate the shortest path length between any point to solve this problem smoothly. /// Set the latitude and longitude of point P to (plat, plong), the latitude and longitude of point Q to (qlat, qlong), and the radius of the Earth to R, // The spherical distance between p and q is (degrees in radians): // D (p, q) = r * arccos (sin (Plat) sin (qlat) + cos (Plat) Cos (qlat) Cos (plong −qlong )) # include <iostream> # include <cmath> # include <map> # include <set> using namespace STD; # define maxn 100 # define maxm 300 # define maxq 10000 # define PI 3.141592653589793 # define earth_radius 6378 # define maxint (1l <20) int weight [m AXN + 1] [maxn + 1]; pair <double, double> locations [maxn + 1]; Map <string, int> cities; // converts degrees to radians. Inline double radians (double degree) {return (degree * 2.0 * PI/360.0);} // calculates the distance between the two cities. Int caldistance (INT start, int end) {// converts degrees to radians. Double plat = radians (locations [start]. first); double plong = radians (locations [start]. second); double qlat = radians (locations [end]. first); double qlong = radians (locations [end]. second); // use the formula to calculate the curve distance between two points on the sphere. Double distance = earth_radius * ACOs (sin (Plat) * sin (qlat) + cos (Plat) * Cos (qlat) * Cos (plong-qlong )); // round the result and return the result. Return (INT) (distance + 0.5);} int main (int ac, char * AV []) {int n, m, Q, cases = 1; bool printsmartemptyline = false; string city, citystart, cityend; double latitude, longpolling; while (CIN> N> m> q, N | M | q) {// initialization. Cities. clear (); For (INT I = 1; I <= maxn; I ++) for (Int J = 1; j <= maxn; j ++) weight [I] [J] = maxint; // read the city and its coordinates. For (INT I = 1; I <= N; I ++) {CIN> city> latitude> longpolling; cities [City] = I; locations [I] = make_pair (latitude, longpolling);} // read route data. For (INT I = 1; I <= m; I ++) {CIN> citystart> cityend; int idstart = cities [citystart]; int idend = cities [cityend]; weight [idstart] [idend] = caldistance (idstart, idend );} // use the Floyd-warshall algorithm to calculate the shortest route distance between any two cities. For (int K = 1; k <= N; k ++) for (INT I = 1; I <= N; I ++) for (Int J = 1; j <= N; j ++) weight [I] [J] = min (weight [I] [J], weight [I] [k] + weight [k] [J]); // empty rows are output. If (printsmartemptyline) cout <Endl; elseprintsmartemptyline = true; // number of output test cases. Cout <"case #" <cases ++ <Endl; // outputs the route distance between cities. For (INT I = 1; I <= Q; I ++) {CIN> citystart> cityend; int idstart = cities [citystart]; int idend = cities [cityend]; If (weight [idstart] [idend] <maxint) cout <weight [idstart] [idend] <"km" <Endl; elsecout <"No route exists" <Endl ;}} return 0 ;}