GeographicLib  2.6
Constants.hpp
Go to the documentation of this file.
1 /**
2  * \file Constants.hpp
3  * \brief Header for GeographicLib::Constants class
4  *
5  * Copyright (c) Charles Karney (2008-2024) <karney@alum.mit.edu> and licensed
6  * under the MIT/X11 License. For more information, see
7  * https://geographiclib.sourceforge.io/
8  **********************************************************************/
9 
10 #if !defined(GEOGRAPHICLIB_CONSTANTS_HPP)
11 #define GEOGRAPHICLIB_CONSTANTS_HPP 1
12 
13 #include <GeographicLib/Config.h>
14 
15 /**
16  * @relates GeographicLib::Constants
17  * Pack the version components into a single integer. Users should not rely on
18  * this particular packing of the components of the version number; see the
19  * documentation for GEOGRAPHICLIB_VERSION, below.
20  **********************************************************************/
21 #define GEOGRAPHICLIB_VERSION_NUM(a,b,c) ((((a) * 10000 + (b)) * 100) + (c))
22 
23 /**
24  * @relates GeographicLib::Constants
25  * The version of GeographicLib as a single integer, packed as MMmmmmpp where
26  * MM is the major version, mmmm is the minor version, and pp is the patch
27  * level. Users should not rely on this particular packing of the components
28  * of the version number. Instead they should use a test such as \code
29  #if GEOGRAPHICLIB_VERSION >= GEOGRAPHICLIB_VERSION_NUM(1,37,0)
30  ...
31  #endif
32  * \endcode
33  **********************************************************************/
34 #define GEOGRAPHICLIB_VERSION \
35  GEOGRAPHICLIB_VERSION_NUM(GEOGRAPHICLIB_VERSION_MAJOR, \
36  GEOGRAPHICLIB_VERSION_MINOR, \
37  GEOGRAPHICLIB_VERSION_PATCH)
38 
39 // For reference, here is a table of Visual Studio and _MSC_VER
40 // correspondences:
41 //
42 // _MSC_VER Visual Studio
43 // 1900 vc14 (2015) First version of VS to include enough C++11 support
44 // 191[0-6] vc15 (2017) First version of VS to include enough C++17 support
45 // 192[0-9] vc16 (2019)
46 // 1930-1944 vc17 (2022)
47 // vc18 (2026)
48 
49 #if defined(_MSC_VER) && defined(GEOGRAPHICLIB_SHARED_LIB) && \
50  GEOGRAPHICLIB_SHARED_LIB
51 # if GEOGRAPHICLIB_SHARED_LIB > 1
52 # error GEOGRAPHICLIB_SHARED_LIB must be 0 or 1
53 # elif defined(GeographicLib_SHARED_EXPORTS)
54 # define GEOGRAPHICLIB_EXPORT __declspec(dllexport)
55 # else
56 # define GEOGRAPHICLIB_EXPORT __declspec(dllimport)
57 # endif
58 #else
59 # define GEOGRAPHICLIB_EXPORT
60 #endif
61 
62 #include <stdexcept>
63 #include <string>
64 #include <GeographicLib/Math.hpp>
65 
66 /**
67  * \brief Namespace for %GeographicLib
68  *
69  * All of %GeographicLib is defined within the GeographicLib namespace. In
70  * addition all the header files are included via GeographicLib/Class.hpp.
71  * This minimizes the likelihood of conflicts with other packages.
72  **********************************************************************/
73 namespace GeographicLib {
74 
75  /**
76  * \brief %Constants needed by %GeographicLib
77  *
78  * Define constants specifying the WGS84 ellipsoid, the UTM and UPS
79  * projections, and various unit conversions.
80  *
81  * Example of use:
82  * \include example-Constants.cpp
83  **********************************************************************/
85  private:
86  typedef Math::real real;
87  Constants() = delete; // Disable constructor
88 
89  public:
90  /**
91  * A synonym for Math::degree<real>().
92  **********************************************************************/
93  static Math::real degree() { return Math::degree(); }
94  /**
95  * @return the number of radians in an arcminute.
96  **********************************************************************/
98  { return Math::degree() / Math::dm; }
99  /**
100  * @return the number of radians in an arcsecond.
101  **********************************************************************/
103  { return Math::degree() / Math::ds; }
104 
105  /** \name Ellipsoid parameters
106  **********************************************************************/
107  ///@{
108  /**
109  * @tparam T the type of the returned value.
110  * @return the equatorial radius of WGS84 ellipsoid (6378137 m).
111  **********************************************************************/
112  template<typename T = real> static T WGS84_a()
113  { return 6378137 * meter<T>(); }
114  /**
115  * @tparam T the type of the returned value.
116  * @return the flattening of WGS84 ellipsoid (1/298.257223563).
117  **********************************************************************/
118  template<typename T = real> static T WGS84_f() {
119  // Evaluating this as 1000000000 / T(298257223563LL) reduces the
120  // round-off error by about 10%. However, expressing the flattening as
121  // 1/298.257223563 is well ingrained.
122  return 1 / ( T(298257223563LL) / 1000000000 );
123  }
124  /**
125  * @tparam T the type of the returned value.
126  * @return the gravitational constant of the WGS84 ellipsoid, \e GM, in
127  * m<sup>3</sup> s<sup>&minus;2</sup>.
128  **********************************************************************/
129  template<typename T = real> static T WGS84_GM()
130  { return T(3986004) * 100000000 + 41800000; }
131  /**
132  * @tparam T the type of the returned value.
133  * @return the angular velocity of the WGS84 ellipsoid, &omega;, in rad
134  * s<sup>&minus;1</sup>.
135  **********************************************************************/
136  template<typename T = real> static T WGS84_omega()
137  { return 7292115 / (T(1000000) * 100000); }
138  /**
139  * @tparam T the type of the returned value.
140  * @return the equatorial radius of GRS80 ellipsoid, \e a, in m.
141  **********************************************************************/
142  template<typename T = real> static T GRS80_a()
143  { return 6378137 * meter<T>(); }
144  /**
145  * @tparam T the type of the returned value.
146  * @return the gravitational constant of the GRS80 ellipsoid, \e GM, in
147  * m<sup>3</sup> s<sup>&minus;2</sup>.
148  **********************************************************************/
149  template<typename T = real> static T GRS80_GM()
150  { return T(3986005) * 100000000; }
151  /**
152  * @tparam T the type of the returned value.
153  * @return the angular velocity of the GRS80 ellipsoid, &omega;, in rad
154  * s<sup>&minus;1</sup>.
155  *
156  * This is about 2 &pi; 366.25 / (365.25 &times; 24 &times; 3600) rad
157  * s<sup>&minus;1</sup>. 365.25 is the number of days in a Julian year and
158  * 365.35/366.25 converts from solar days to sidereal days. Using the
159  * number of days in a Gregorian year (365.2425) results in a worse
160  * approximation (because the Gregorian year includes the precession of the
161  * earth's axis).
162  **********************************************************************/
163  template<typename T = real> static T GRS80_omega()
164  { return 7292115 / (T(1000000) * 100000); }
165  /**
166  * @tparam T the type of the returned value.
167  * @return the dynamical form factor of the GRS80 ellipsoid,
168  * <i>J</i><sub>2</sub>.
169  **********************************************************************/
170  template<typename T = real> static T GRS80_J2()
171  { return T(108263) / 100000000; }
172  /**
173  * @tparam T the type of the returned value.
174  * @return the central scale factor for UTM (0.9996).
175  **********************************************************************/
176  template<typename T = real> static T UTM_k0()
177  {return T(9996) / 10000; }
178  /**
179  * @tparam T the type of the returned value.
180  * @return the central scale factor for UPS (0.994).
181  **********************************************************************/
182  template<typename T = real> static T UPS_k0()
183  { return T(994) / 1000; }
184  ///@}
185 
186  /** \name Triaxial ellipsoid parameters
187  *
188  * These parameters are close to the values given by Milan Bursa, Vladimira
189  * Fialova, "Parameters of the Earth's tri-axial level ellipsoid", Studia
190  * Geophysica et Geodaetica 37(1), 1-13 (1993).
191  * - longitude of major axis = &minus;14.93&deg; &plusmn; 0.05&deg;
192  * - \e a = 6378171.36 m &plusmn; 0.30 m
193  * - \e a / (\e a &minus; \e c) = 297.7738 &plusmn; 0.0003
194  * - \e a / (\e a &minus; \e b) = 91449 &plusmn; 60
195  * .
196  * which gives: \e a = 6378171.36 m, \e b = 6378101.61 m, \e c = 6356751.84
197  * m. Here take the semiaxes to be whole numbers of meters, with (\e a +
198  * \e b)/2 = WGS84_a(), \e a &minus; \e b = 70 m, \e c = round(WGS84_a() *
199  * (1 - WGS84_f())). This gives
200  * - \e a = 6378172 m
201  * - \e b = 6378102 m
202  * - \e c = 6356752 m
203  * - \e lon0 = &minus;14.93&deg;
204  **********************************************************************/
205  ///@{
206  /**
207  * @tparam T the type of the returned value.
208  * @return the major semiaxis of a triaxial approximation to the Earth, \e
209  * a, in m (= 6378172).
210  **********************************************************************/
211  template<typename T = real> static T Triaxial_Earth_a()
212  { return WGS84_a<T>() + 70/real(2); }
213  /**
214  * @tparam T the type of the returned value.
215  * @return the median semiaxis of a triaxial approximation to the Earth, \e
216  * b, in m (= 6378102).
217  **********************************************************************/
218  template<typename T = real> static T Triaxial_Earth_b()
219  { return WGS84_a<T>() - 70/real(2); }
220  /**
221  * @tparam T the type of the returned value.
222  * @return the minor semiaxis of a triaxial approximation to the Earth, \e
223  * c, in m (= 6356752).
224  **********************************************************************/
225  template<typename T = real> static T Triaxial_Earth_c()
226  { using std::round; return round(WGS84_a<T>() * (1 - WGS84_f())); }
227  /**
228  * @tparam T the type of the returned value.
229  * @return the longitude, with respect to Greenwich, of the major semiaxis
230  * of of a triaxial approximation to the Earth, \e lon0, in degrees (=
231  * &minus;14.93).
232  **********************************************************************/
233  template<typename T = real> static T Triaxial_Earth_lon0()
234  { return T(1493) / 100; }
235  ///@}
236 
237  /** \name SI units
238  **********************************************************************/
239  ///@{
240  /**
241  * @tparam T the type of the returned value.
242  * @return the number of meters in a meter.
243  *
244  * This is unity, but this lets the internal system of units be changed if
245  * necessary.
246  **********************************************************************/
247  template<typename T = real> static T meter() { return T(1); }
248  /**
249  * @return the number of meters in a kilometer.
250  **********************************************************************/
252  { return 1000 * meter<real>(); }
253  /**
254  * @return the number of meters in a nautical mile (approximately 1 arc
255  * minute)
256  **********************************************************************/
258  { return 1852 * meter<real>(); }
259 
260  /**
261  * @tparam T the type of the returned value.
262  * @return the number of square meters in a square meter.
263  *
264  * This is unity, but this lets the internal system of units be changed if
265  * necessary.
266  **********************************************************************/
267  template<typename T = real> static T square_meter()
268  { return meter<T>() * meter<T>(); }
269  /**
270  * @return the number of square meters in a hectare.
271  **********************************************************************/
273  { return 10000 * square_meter<real>(); }
274  /**
275  * @return the number of square meters in a square kilometer.
276  **********************************************************************/
278  { return kilometer() * kilometer(); }
279  /**
280  * @return the number of square meters in a square nautical mile.
281  **********************************************************************/
283  { return nauticalmile() * nauticalmile(); }
284  ///@}
285 
286  /** \name Anachronistic British units
287  **********************************************************************/
288  ///@{
289  /**
290  * @return the number of meters in an international foot.
291  **********************************************************************/
292  static Math::real foot()
293  { return real(254 * 12) / 10000 * meter<real>(); }
294  /**
295  * @return the number of meters in a yard.
296  **********************************************************************/
297  static Math::real yard() { return 3 * foot(); }
298  /**
299  * @return the number of meters in a fathom.
300  **********************************************************************/
301  static Math::real fathom() { return 2 * yard(); }
302  /**
303  * @return the number of meters in a chain.
304  **********************************************************************/
305  static Math::real chain() { return 22 * yard(); }
306  /**
307  * @return the number of meters in a furlong.
308  **********************************************************************/
309  static Math::real furlong() { return 10 * chain(); }
310  /**
311  * @return the number of meters in a statute mile.
312  **********************************************************************/
313  static Math::real mile() { return 8 * furlong(); }
314  /**
315  * @return the number of square meters in an acre.
316  **********************************************************************/
317  static Math::real acre() { return chain() * furlong(); }
318  /**
319  * @return the number of square meters in a square statute mile.
320  **********************************************************************/
321  static Math::real square_mile() { return mile() * mile(); }
322  ///@}
323 
324  /** \name Anachronistic US units
325  **********************************************************************/
326  ///@{
327  /**
328  * @return the number of meters in a US survey foot.
329  **********************************************************************/
331  { return real(1200) / 3937 * meter<real>(); }
332  ///@}
333  };
334 
335  /**
336  * \brief Exception handling for %GeographicLib
337  *
338  * A class to handle exceptions. It's derived from std::runtime_error so it
339  * can be caught by the usual catch clauses.
340  *
341  * Example of use:
342  * \include example-GeographicErr.cpp
343  **********************************************************************/
344  class GeographicErr : public std::runtime_error {
345  public:
346 
347  /**
348  * Constructor
349  *
350  * @param[in] msg a string message, which is accessible in the catch
351  * clause via what().
352  **********************************************************************/
353  GeographicErr(const std::string& msg) : std::runtime_error(msg) {}
354  };
355 
356 } // namespace GeographicLib
357 
358 #endif // GEOGRAPHICLIB_CONSTANTS_HPP
static Math::real arcminute()
Definition: Constants.hpp:97
static Math::real mile()
Definition: Constants.hpp:313
static Math::real kilometer()
Definition: Constants.hpp:251
static Math::real yard()
Definition: Constants.hpp:297
#define GEOGRAPHICLIB_EXPORT
Definition: Constants.hpp:59
static Math::real square_nauticalmile()
Definition: Constants.hpp:282
static constexpr int ds
seconds per degree
Definition: Math.hpp:147
static Math::real nauticalmile()
Definition: Constants.hpp:257
static T Triaxial_Earth_lon0()
Definition: Constants.hpp:233
static Math::real arcsecond()
Definition: Constants.hpp:102
static Math::real foot()
Definition: Constants.hpp:292
static Math::real surveyfoot()
Definition: Constants.hpp:330
static Math::real furlong()
Definition: Constants.hpp:309
static Math::real hectare()
Definition: Constants.hpp:272
static Math::real degree()
Definition: Constants.hpp:93
static Math::real fathom()
Definition: Constants.hpp:301
static constexpr int dm
minutes per degree
Definition: Math.hpp:143
static Math::real acre()
Definition: Constants.hpp:317
Header for GeographicLib::Math class.
static Math::real chain()
Definition: Constants.hpp:305
Namespace for GeographicLib.
Definition: Accumulator.cpp:12
static T degree()
Definition: Math.hpp:197
GeographicLib::Math::real real
Definition: Geod3Solve.cpp:25
Constants needed by GeographicLib
Definition: Constants.hpp:84
Exception handling for GeographicLib.
Definition: Constants.hpp:344
static Math::real square_kilometer()
Definition: Constants.hpp:277
static Math::real square_mile()
Definition: Constants.hpp:321
GeographicErr(const std::string &msg)
Definition: Constants.hpp:353