GeographicLib  2.6
Angle.hpp
Go to the documentation of this file.
1 /**
2  * \file Angle.hpp
3  * \brief Header for the GeographicLib::AngleT class
4  *
5  * The class provide an accurate representation of angle via 3 numbers, its
6  * sine and cosine, and the number of turns.
7  *
8  * Copyright (c) Charles Karney (2024-2025) <karney@alum.mit.edu> and licensed
9  * under the MIT/X11 License. For more information, see
10  * https://geographiclib.sourceforge.io/
11  **********************************************************************/
12 
13 #if !defined(GEOGRAPHICLIB_ANGLE_HPP)
14 #define GEOGRAPHICLIB_ANGLE_HPP 1
15 
16 #include <string>
17 #include <GeographicLib/Math.hpp>
18 
19 namespace GeographicLib {
20 
21  /**
22  * \brief An accurate representation of angles.
23  *
24  * @tparam T the working floating point type.
25  *
26  * This class provides an accurate representation of angle via 3 numbers, its
27  * sine = \e s and cosine = \e c, and the number of turns = \e n. The angle
28  * is then 2\e n &pi; + atan2(\e s, \e c). This representation offers
29  * several advantages:
30  * - the cardinal directors (multiples of 90&deg;) are exactly represented (a
31  * benefit shared by representing angles as degrees);
32  * - angles very close to any cardinal direction are accurately represented;
33  * - there's no loss of precision with large angles (outside the "normal"
34  * range [&minus;180&deg;, +180&deg;]);
35  * - various operations, such as adding a multiple of 90&deg; to an angle are
36  * performed exactly.
37  * .
38  * This representation does not favor degrees over radians. However, the
39  * one-argument constructor, AngleT(T), does the conversion from degrees and
40  * the cast to T, AngleT::operator T(), returns the angle in degrees. There
41  * are alternatives, radians(T) and radians() const, to allow these
42  * conversions with radians.
43  *
44  * N.B. \e n is stored as a real. This allows it to be inf or nan.
45  *
46  * Example of use:
47  * \include example-Angle.cpp
48  **********************************************************************/
49  template<typename T = Math::real>
50  class AngleT {
51  // No GEOGRAPHICLIB_EXPORT because this is a template class (like
52  // PolygonAreaT). Not sure why Accumulator needs GEOGRAPHICLIB_EXPORT.
53  private:
54  T _s, _c, _n;
55  static T rnd(T x);
56  public:
57  /** \name Creating AngleT objects.
58  **********************************************************************/
59  ///@{
60  /**
61  * The default constructor.
62  *
63  * This sets the angle to 0.
64  **********************************************************************/
65  AngleT() : _s(0), _c(1), _n(0) {}
66  /**
67  * The general constructor.
68  *
69  * @param[in] s the sine component.
70  * @param[in] c the cosine component.
71  * @param[in] num the number of turns (default 0).
72  * @param[in] normp are \e s and \e c normalized (default false).
73  *
74  * \warning either \e s or \e c can be infinite, but not both.
75  *
76  * By default, the point (\e s, \e c) is scaled to lie on the unit circle.
77  * Setting \e normp = true skips this step; in this case (\e s, \e c)
78  * should already lie on the unit circle.
79  **********************************************************************/
80  AngleT(T s, T c, T num = 0, bool normp = false);
81  /**
82  * The 1-argument constructor.
83  *
84  * @param[in] deg the angle in degrees.
85  *
86  * \note This is an explicit constructor to avoid accidental conversions.
87  **********************************************************************/
88  explicit AngleT(T deg);
89  /**
90  * The convert an angle in degrees to an AngleT.
91  *
92  * @param[in] deg the angle in degrees.
93  * @return the AngleT.
94  *
95  * \note This mimics the behavior of AngleT(T deg);
96  **********************************************************************/
97  static AngleT degrees(T deg);
98  /**
99  * Convert an angle in radians to an AngleT.
100  *
101  * @param[in] rad the angle in radians.
102  * @return the AngleT.
103  *
104  * \note This is the radians analog of degrees(T).
105  **********************************************************************/
106  static AngleT radians(T rad);
107  /**
108  * Convert an lambertian to an AngleT.
109  *
110  * @param[in] q the lambertian of the angle.
111  * @return the AngleT.
112  *
113  * This sets the angle to atan(sinh(\e q)).
114  **********************************************************************/
115  static AngleT lam(T q);
116  /**
117  * Not an angle.
118  *
119  * @return the AngleT equivalent to not-a-number.
120  **********************************************************************/
121  static AngleT NaN();
122  /**
123  * A cardinal direction.
124  *
125  * @param[in] q the number of quarter turns.
126  * @return the AngleT equivalent to \e q quarter turns.
127  *
128  * \e q is rounded to an integer and \e q = &plusmn;0 are distinguished.
129  * NaN() is returned is \e q is not finite.
130  **********************************************************************/
131  static AngleT cardinal(T q);
132  /**
133  * Return a tiny angle.
134  *
135  * @return a tiny angle.
136  *
137  * This allows angles extremely close to the cardinal directions to be
138  * generated. The round() function will flush this angle to 0.
139  **********************************************************************/
140  static AngleT eps();
141  ///@}
142 
143  /** \name Inspector functions.
144  **********************************************************************/
145  ///@{
146  /**
147  * @return the sine of the angle.
148  **********************************************************************/
149  T s() const { return _s; }
150  /**
151  * @return the cosine of the angle.
152  **********************************************************************/
153  T c() const { return _c; }
154  /**
155  * @return the tangent of the angle.
156  **********************************************************************/
157  T t() const { return _s/_c; }
158  /**
159  * @return the number of turns.
160  **********************************************************************/
161  T n() const {
162  return _n + 0; // Convert -0 to +0
163  }
164  /**
165  * @return the number of turns treating &minus;180&deg; as +180&deg; less 1
166  * turn.
167  **********************************************************************/
168  T n0() const;
169  ///@}
170 
171  /** \name Converting AngleT into other representations
172  **********************************************************************/
173  ///@{
174  /**
175  * Convert an AngleT to degrees via a type conversion.
176  *
177  * @return the angle in degrees.
178  *
179  * \note This is an explicit type conversion to avoid accidental
180  * conversions.
181  **********************************************************************/
182  explicit operator T() const;
183  /**
184  * Convert an AngleT to degrees.
185  *
186  * @return the angle in degrees.
187  *
188  * \note This mimics the behavior of AngleT::operator T().
189  **********************************************************************/
190  T degrees() const;
191  /**
192  * Convert an AngleT to degrees ignoring the number of turns.
193  *
194  * @return the angle in degrees assuming n() is zero.
195  **********************************************************************/
196  T degrees0() const;
197  /**
198  * Convert an AngleT to radians.
199  *
200  * @return the angle in radians.
201  *
202  * \note This is the radians analog of degrees().
203  **********************************************************************/
204  T radians() const;
205  /**
206  * Convert an AngleT to radians ignoring the number of turns.
207  *
208  * @return the angle in radians assuming n() is zero.
209  *
210  * \note This is the radians analog of degrees0().
211  **********************************************************************/
212  T radians0() const;
213  /**
214  * Return the lambertian of the AngleT.
215  *
216  * @return the lambertian.
217  *
218  * The lambertian of &phi; is asinh tan &phi;.
219  **********************************************************************/
220  T lam() const;
221  /**
222  * Return the nearest cardinal direction as an AngleT.
223  *
224  * @param[in] ind an indicator.
225  * @return the nearest cardinal direction as an AngleT.
226  *
227  * If \e ind == 0 (the default) the closest cardinal direction is returned.
228  * Otherwise, if \e ind is even, the closest even (N/S) cardinal direction
229  * is returned; or, if \e ind is odd, the closest odd (E/W) cardinal
230  * direction is returned.
231  **********************************************************************/
232  AngleT nearest(unsigned ind = 0U) const;
233  /**
234  * Return the nearest cardinal direction as an integer.
235  *
236  * @return the nearest cardinal direction as an integer.
237  *
238  * \note This is the reverse of cardinal(T).
239  **********************************************************************/
240  T ncardinal() const;
241  unsigned quadrant() const;
242  ///@}
243 
244  /** \name Elementary arithmetic operations on AngleT
245  **********************************************************************/
246  ///@{
247  /**
248  * Return the negated AngleT.
249  *
250  * @return minus the AngleT
251  **********************************************************************/
252  AngleT operator-() const;
253  /**
254  * Implement the += operator.
255  *
256  * @param[in] p the AngleT to be added.
257  * @return the current AngleT after the addition.
258  **********************************************************************/
259  AngleT& operator+=(const AngleT& p);
260  /**
261  * Implement the -= operator.
262  *
263  * @param[in] p the AngleT to be subtracted.
264  * @return the current AngleT after the subtraction.
265  **********************************************************************/
266  AngleT& operator-=(const AngleT& p);
267  /**
268  * Implement the + operator.
269  *
270  * @param[in] p the AngleT to be added.
271  * @return the result of the addition; the current AngleT is not modified.
272  **********************************************************************/
273  AngleT operator+(const AngleT& p) const;
274  /**
275  * Implement the - operator.
276  *
277  * @param[in] p the AngleT to be subtracted.
278  * @return the result of the subtraction; the current AngleT is not
279  * modified.
280  **********************************************************************/
281  AngleT operator-(const AngleT& p) const;
282  /**
283  * Test for a zero angle.
284  *
285  * @param[in] mult multiplier of machine epsilon used in test (default 0).
286  * @return true if this AngleT is withing \e mult &epsilon; of zero.
287  **********************************************************************/
288  bool zerop(T mult = 0) const;
289  /**
290  * Implement the == operator.
291  *
292  * @param[in] p the AngleT to be compared against
293  * @return *this == \e p.
294  **********************************************************************/
295  bool operator==(const AngleT& p) const;
296  ///@}
297 
298  /** \name Operations which modify a AngleT
299  **********************************************************************/
300  ///@{
301  /**
302  * "Round" the AngleT the == operator.
303  *
304  * @return the AngleT with tiny values of s() and c() set to &plusmn;0.
305  *
306  * This ensures that the smallest gaps between sine and cosine values is
307  * &epsilon;/2048.
308  **********************************************************************/
309  AngleT& round();
310  /**
311  * Renormalize the sine and cosine values
312  *
313  * @return the modified AngleT.
314  *
315  * During arithmetic operations on AngleT object, no effort is mode to
316  * ensure that (s(), c()) remains on the unit circle. This function
317  * corrects this.
318  **********************************************************************/
319  AngleT& renormalize();
320  /**
321  * Reduce the angle to [&minus;180&deg;, +180&deg;]
322  *
323  * @return the modified AngleT, obtained by setting n() to zero.
324  **********************************************************************/
325  AngleT& setn(T n = 0);
326  /**
327  * Reduce the angle to (&minus;180&deg;, +180&deg;]
328  *
329  * @return the modified AngleT.
330  *
331  * This differs from setn(T) by treating &minus;180&deg; as +180&deg; less
332  * 1 turn.
333  **********************************************************************/
334  AngleT& setn0(T n = 0);
335  /**
336  * Set the quadrant of an AngleT the angle to (&minus;180&deg;, +180&deg;]
337  *
338  * @param[in] q the quadrant.
339  * @return the modified AngleT.
340  *
341  * This sets the signs of s() and c() according to e q.
342  *
343  * \note Only the low two bits of \e q are used. n() is unchanged.
344  **********************************************************************/
345  AngleT& setquadrant(unsigned q);
346  /**
347  * Reflect the angle is various ways
348  *
349  * @param[in] flips change the sign of s()
350  * @param[in] flipc change the sign of c()
351  * @param[in] swapp swap s() and c()
352  * @return the modified AngleT.
353  *
354  * \note The operations are carried out in the order of the parameters.
355  **********************************************************************/
356  AngleT& reflect(bool flips, bool flipc = false, bool swapp = false);
357  ///@}
358 
359  /** \name Operations which return a new AngleT
360  **********************************************************************/
361  ///@{
362  /**
363  * Return an AngleT in [&minus;180&deg;, +180&deg;].
364  *
365  * @return the new AngleT.
366  *
367  * This returns the AngleT with n() set to zero.
368  **********************************************************************/
369  AngleT base() const;
370  /**
371  * Return an AngleT centered about another AngleT
372  *
373  * @param[in] c the center AngleT
374  * @return the new AngleT.
375  *
376  * This returns the result of adjusting n() so that the new AngleT is with
377  * &plusmn;180&deg; of \e c.
378  **********************************************************************/
379  AngleT rebase(const AngleT& c) const;
380  /**
381  * Return an AngleT with the sign optionally flipped
382  *
383  * @param[in] mult
384  * @return the new AngleT.
385  *
386  * return signbit(\e mult) ? -*this : *this.
387  **********************************************************************/
388  AngleT flipsign(T mult) const;
389  /**
390  * The "reduced latitude" operation.
391  *
392  * @param[in] m
393  * @return the atan(m * tan(*this))
394  *
395  * However the quadrant of the result tracking that of *this through
396  * multiples turns.
397  **********************************************************************/
398  AngleT modang(T m) const;
399  ///@}
400 
401  /** \name Converting AngleT to and from a string representation
402  **********************************************************************/
403  ///@{
404  /**
405  * Interpret two strings as latitude and longitude.
406  *
407  * @param[in] stra the first string
408  * @param[in] strb the second string
409  * @param[out] lat the latitude
410  * @param[out] lon the longitude
411  * @param[in] longfirst (defaultfirst) whether the longitude is given
412  * first.
413  *
414  * In the absence of hemisphere indicators (N/S for latitude and E/W for
415  * longitude), it is assumed that the first string is the latitude.
416  * Setting \e longfirst = true uses the opposite convention. The
417  * hemisphere indicators can also be used to set the signs of the angles.
418  **********************************************************************/
419  static void DecodeLatLon(const std::string& stra, const std::string& strb,
420  AngleT& lat, AngleT& lon,
421  bool longfirst = false);
422  /**
423  * Interpret a string as azimuth
424  *
425  * @param[in] azistr the string representing the azimuth
426  * @return the azimuth
427  *
428  * The hemisphere indicators E/W can be used to set the sign of the
429  * azimuth.
430  **********************************************************************/
431  static AngleT DecodeAzimuth(const std::string& azistr);
432  /**
433  * Create a string for a latitude-longitude pair.
434  *
435  * @param[in] lat the latitude.
436  * @param[in] lon the longitude.
437  * @param[in] prec the precision relative to 1&deg;.
438  * @param[in] dms (default false) whether to use degrees/minutes/seconds as
439  * opposed to decimal degrees
440  * @param[in] dmssep (default NULL) the separator to use with the DMS
441  * representation instead of d ' ".
442  * @param[in] longfirst (default false) whether to list the longitude
443  * first.
444  * @return string representation
445  *
446  * With dms = true the hemisphere indicators N/S and E/W are used to
447  * indicator the signs of the latitude and longitude.
448  **********************************************************************/
449  static std::string LatLonString(AngleT lat, AngleT lon, int prec,
450  bool dms = false, char dmssep = '\0',
451  bool longfirst = false);
452  /**
453  * Create a string for an azimuth.
454  *
455  * @param[in] azi the azimuth.
456  * @param[in] prec the precision relative to 1&deg;.
457  * @param[in] dms (default false) whether to use degrees/minutes/seconds as
458  * opposed to decimal degrees
459  * @param[in] dmssep (default NULL) the separator to use with the DMS
460  * representation instead of d ' ".
461  * @return string representation
462  *
463  * With dms = true the hemisphere indicators and E/W is used to
464  * indicator the sign of the azimuth.
465  **********************************************************************/
466  static std::string AzimuthString(AngleT azi, int prec,
467  bool dms = false, char dmssep = '\0');
468  ///@}
469  };
470 
471  template<typename T>
472  inline AngleT<T>::AngleT(T s, T c, T num, bool normp)
473  : _s(s)
474  , _c(c)
475  , _n(num)
476  {
477  using std::isfinite, std::isnan, std::isinf, std::hypot,
478  std::copysign, std::rint;
479  _n = rint(_n);
480  if (!normp) {
481  // Cannot just use Math::norm because of all the special cases
482  T h = hypot(_s, _c);
483  if (h == 0) {
484  // If y is +/-0 and x = -0, +/-pi is returned.
485  // If y is +/-0 and x = +0, +/-0 is returned.
486  // So retain the sign of _s = +/-0
487  _c = copysign(T(1), _c);
488  } else if (isfinite(h)) {
489  _s /= h; _c /= h;
490  } else if (isnan(h) || (isinf(_s) && isinf(_c)))
491  _s = _c = Math::NaN();
492  else if (isinf(_s)) {
493  // infinite, finite
494  _s = copysign(T(1), _s);
495  _c = copysign(T(0), _c);
496  } else {
497  // isinf(cos); finite, infinite
498  _s = copysign(T(0), _s);
499  _c = copysign(T(1), _c);
500  }
501  }
502  }
503 
504  template<typename T>
505  inline AngleT<T>::AngleT(T deg) {
506  using std::rint;
507  Math::sincosd(deg, _s, _c);
508  _n = rint( (deg - Math::atan2d(_s, _c)) / Math::td );
509  }
510 
511  template<typename T>
512  inline AngleT<T>::operator T() const {
513  T d = degrees0();
514  // Preserve sign of +/-0
515  return _n == 0 ? d : d + Math::td * _n;
516  }
517 
518  template<typename T>
520  return AngleT<T>(deg);
521  }
522 
523  template<typename T>
524  inline T AngleT<T>::degrees() const {
525  return T(*this);
526  }
527 
528  template<typename T>
529  inline T AngleT<T>::degrees0() const {
530  return Math::atan2d(_s, _c);
531  }
532 
533  template<typename T>
535  using std::sin, std::cos, std::atan2, std::rint;
536  T sn = sin(rad), cs = cos(rad);
537  return AngleT<T>(sn, cs, rint( (rad - atan2(sn, cs)) / (2 * Math::pi()) ),
538  true);
539  }
540 
541  template<typename T>
542  inline T AngleT<T>::radians() const {
543  T r = radians0();
544  // Preserve sign of +/-0
545  return _n == 0 ? r : r + 2 * Math::pi() * _n;
546  }
547 
548  template<typename T>
549  inline T AngleT<T>::radians0() const {
550  using std::atan2;
551  return atan2(_s, _c);
552  }
553 
554  template<typename T>
555  inline AngleT<T> AngleT<T>::lam(T psi) {
556  using std::sinh;
557  return AngleT<T>(sinh(psi), 1, 0);
558  }
559 
560  template<typename T>
561  inline T AngleT<T>::lam() const {
562  using std::asinh;
563  return asinh(t());
564  }
565 
566  template<typename T>
568  return AngleT<T>(Math::NaN(), Math::NaN(), 0, true);
569  }
570 
571  template<typename T>
572  inline T AngleT<T>::ncardinal() const {
573  using std::signbit, std::fabs;
574  int iq = (signbit(_s) ? -1 : 1) * (signbit(_c) ?
575  ( -_c >= fabs(_s) ? 2 : 1 ) :
576  ( _c >= fabs(_s) ? 0 : 1 ));
577  return 4 * _n + iq;
578  }
579 
580  template<typename T>
582  return AngleT<T>(std::numeric_limits<T>::epsilon() / (1 << 20), 1, 0, true);
583  }
584 
585  // AngleT<T> AngleT<T>::operator+() const { return *this; }
586  template<typename T>
588  return AngleT<T>(-_s, _c, -_n, true);
589  }
590 
591  template<typename T>
593  using std::rint;
594  T q = ncardinal() + p.ncardinal();
595  T c = _c * p._c - _s * p._s;
596  _s = _s * p._c + _c * p._s;
597  _c = c;
598  _n += p._n;
599  q -= ncardinal();
600  _n += rint(q / 4);
601  return *this;
602  }
603 
604  template<typename T>
605  inline AngleT<T> AngleT<T>::operator+(const AngleT<T>& p) const {
606  AngleT<T> t = *this; t += p;
607  return t;
608  }
609 
610  template<typename T>
612  *this += -p;
613  return *this;
614  }
615 
616  template<typename T>
617  inline AngleT<T> AngleT<T>::operator-(const AngleT<T>& p) const {
618  AngleT<T> t = *this; t -= p;
619  return t;
620  }
621 
622  template<typename T>
623  inline bool AngleT<T>::zerop(T mult) const {
624  using std::fabs;
625  return _n == 0 &&_c > 0 &&
626  fabs(_s) <= mult * std::numeric_limits<T>::epsilon();
627  }
628 
629  template<typename T>
630  inline bool AngleT<T>::operator==(const AngleT<T>& p) const {
631  AngleT<T> t = *this; t -= p;
632  return t.zerop();
633  }
634 
635  template<typename T>
637  _s = rnd(_s); _c = rnd(_c);
638  return *this;
639  }
640 
641  template<typename T>
642  inline AngleT<T> AngleT<T>::base() const {
643  return AngleT<T>(_s, _c, 0, true);
644  }
645 
646  template<typename T>
647  inline AngleT<T> AngleT<T>::rebase(const AngleT<T>& c) const {
648  // This is exact for c = cardinal direction
649  // return (*this - c).base() + c;
650  AngleT<T> t = *this;
651  return t.setn0(((*this - c).base() + c).n0());
652  }
653 
654  template<typename T>
656  using std::hypot;
657  T h = hypot(_s, _c); _s /= h; _c /= h;
658  return *this;
659  }
660 
661  template<typename T>
662  inline AngleT<T>& AngleT<T>::setn(T n) {
663  using std::rint;
664  _n = rint(n);
665  return *this;
666  }
667 
668  template<typename T>
669  inline T AngleT<T>::n0() const {
670  using std::signbit;
671  return (_n - (_s == 0 && signbit(_s) && _c < 0 ? 1 : 0)) + 0;
672  }
673 
674  template<typename T>
676  using std::rint, std::signbit;
677  _n = rint(n) + (_s == 0 && signbit(_s) && _c < 0 ? 1 : 0);
678  return *this;
679  }
680 
681  template<typename T>
682  inline AngleT<T>& AngleT<T>::setquadrant(unsigned q) {
683  using std::copysign;
684  _s = copysign(_s, T( q & 2U ? -1 : 1 ));
685  _c = copysign(_c, T( ((q >> 1) ^ q) & 1U ? -1 : 1 ));
686  return *this;
687  }
688 
689  template<typename T>
690  inline unsigned AngleT<T>::quadrant() const {
691  using std::signbit;
692  return 2U * signbit(_s) + (signbit(_c) ^ signbit(_s));
693  }
694 
695  template<typename T>
696  inline AngleT<T>& AngleT<T>::reflect(bool flips, bool flipc, bool swapp) {
697  using std::swap;
698  if (flips) _s *= -1;
699  if (flipc) _c *= -1;
700  if (swapp) swap(_s, _c);
701  return *this;
702  }
703 
704  template<typename T>
705  inline AngleT<T> AngleT<T>::flipsign(T mult) const {
706  using std::signbit;
707  return signbit(mult) ? -*this : *this;
708  }
709 
710  template<typename T>
711  inline AngleT<T> AngleT<T>::modang(T m) const {
712  using std::signbit;
713  return signbit(m) ? AngleT<T>::NaN() :
714  // Avoid nans if m == inf.
715  AngleT<T>( _s * (m > 1 ? 1 : m),
716  _c / (m > 1 ? m : 1),
717  _n );
718  }
719 
720  template<typename T>
722  using std::isfinite, std::rint, std::remainder;
723  if (!isfinite(q)) return AngleT<T>::NaN();
724  q = rint(q);
725  int iq = int(remainder(q, T(4)));
726  // iq is in [-2, 2];
727  // We could fold iq = -2 to iq = 2; but this way works too.
728  T s, c, z = 0;
729  switch (iq) {
730  case -2: s = -z; c = -1; break;
731  case -1: s = -1; c = z; break;
732  case 1: s = 1; c = z; break;
733  case 2: s = z; c = -1; break;
734  default:
735  // iq = 0, but distinguish q = +/-0
736  s = q != 0 ? z : q; c = 1;
737  break;
738  }
739  return AngleT<T>(s, c, rint((q - iq) / 4), true);
740  }
741 
742  template<typename T>
743  inline AngleT<T> AngleT<T>::nearest(unsigned ind) const {
744  using std::fabs, std::copysign;
745  T s, c;
746  if (ind == 0U) {
747  if (fabs(_c) >= fabs(_s)) {
748  s = copysign(T(0), _s); c = copysign(T(1), _c);
749  } else {
750  s = copysign(T(1), _s); c = copysign(T(0), _c);
751  }
752  } else if ((ind & 1U) == 0U) { // ind nonzero and even
753  s = copysign(T(0), _s); c = copysign(T(1), _c);
754  } else { // ind odd
755  s = copysign(T(1), _s); c = copysign(T(0), _c);
756  }
757  return AngleT<T>(s, c, _n, true);
758  }
759 
761 
762 } // namespace GeographicLib
763 
764 #endif // GEOGRAPHICLIB_ANGLE_HPP
AngleT & operator+=(const AngleT &p)
Definition: Angle.hpp:592
static void DecodeLatLon(const std::string &stra, const std::string &strb, AngleT &lat, AngleT &lon, bool longfirst=false)
Definition: Angle.cpp:39
AngleT & renormalize()
Definition: Angle.hpp:655
T radians0() const
Definition: Angle.hpp:549
AngleT & operator-=(const AngleT &p)
Definition: Angle.hpp:611
AngleT operator-() const
Definition: Angle.hpp:587
bool zerop(T mult=0) const
Definition: Angle.hpp:623
An accurate representation of angles.
Definition: Angle.hpp:50
static AngleT NaN()
Definition: Angle.hpp:567
AngleT & reflect(bool flips, bool flipc=false, bool swapp=false)
Definition: Angle.hpp:696
AngleT nearest(unsigned ind=0U) const
Definition: Angle.hpp:743
T ncardinal() const
Definition: Angle.hpp:572
AngleT operator+(const AngleT &p) const
Definition: Angle.hpp:605
static AngleT cardinal(T q)
Definition: Angle.hpp:721
AngleT & setn(T n=0)
Definition: Angle.hpp:662
Header for GeographicLib::Math class.
T radians() const
Definition: Angle.hpp:542
static AngleT DecodeAzimuth(const std::string &azistr)
Definition: Angle.cpp:62
AngleT & setquadrant(unsigned q)
Definition: Angle.hpp:682
unsigned quadrant() const
Definition: Angle.hpp:690
Namespace for GeographicLib.
Definition: Accumulator.cpp:12
static std::string AzimuthString(AngleT azi, int prec, bool dms=false, char dmssep='\0')
Definition: Angle.cpp:86
bool operator==(const AngleT &p) const
Definition: Angle.hpp:630
T degrees() const
Definition: Angle.hpp:524
AngleT flipsign(T mult) const
Definition: Angle.hpp:705
void swap(GeographicLib::NearestNeighbor< dist_t, pos_t, distfun_t > &a, GeographicLib::NearestNeighbor< dist_t, pos_t, distfun_t > &b)
AngleT & setn0(T n=0)
Definition: Angle.hpp:675
AngleT modang(T m) const
Definition: Angle.hpp:711
static std::string LatLonString(AngleT lat, AngleT lon, int prec, bool dms=false, char dmssep='\0', bool longfirst=false)
Definition: Angle.cpp:72
AngleT base() const
Definition: Angle.hpp:642
AngleT rebase(const AngleT &c) const
Definition: Angle.hpp:647
static AngleT eps()
Definition: Angle.hpp:581
AngleT & round()
Definition: Angle.hpp:636
T degrees0() const
Definition: Angle.hpp:529