GeographicLib 2.2
AuxAngle.hpp
Go to the documentation of this file.
1/**
2 * \file AuxAngle.hpp
3 * \brief Header for the GeographicLib::AuxAngle class
4 *
5 * This file is an implementation of the methods described in
6 * - C. F. F. Karney,
7 * On auxiliary latitudes,
8 * Technical Report, SRI International, December 2022.
9 * https://arxiv.org/abs/2212.05818
10 * .
11 * Copyright (c) Charles Karney (2022-2023) <charles@karney.com> and licensed
12 * under the MIT/X11 License. For more information, see
13 * https://geographiclib.sourceforge.io/
14 **********************************************************************/
15
16#if !defined(GEOGRAPHICLIB_AUXANGLE_HPP)
17#define GEOGRAPHICLIB_AUXANGLE_HPP 1
18
20
21namespace GeographicLib {
22
23 /**
24 * \brief An accurate representation of angles.
25 *
26 * This class is an implementation of the methods described in
27 * - C. F. F. Karney,
28 * On auxiliary latitudes,
29 * Technical Report, SRI International, December 2022.
30 * https://arxiv.org/abs/2212.05818
31 *
32 * An angle is represented be the \e y and \e x coordinates of a point in the
33 * 2d plane. The two coordinates are proportional to the sine and cosine of
34 * the angle. This allows angles close to the cardinal points to be
35 * represented accurately. It also saves on unnecessary recomputations of
36 * trigonometric functions of the angle. Only angles in [&minus;180&deg;,
37 * 180&deg;] can be represented. (A possible extension would be to keep
38 * count of the number of turns.)
39 *
40 * Example of use:
41 * \include example-AuxAngle.cpp
42 **********************************************************************/
44 private:
45 typedef Math::real real;
46 real _y, _x;
47 public:
48 /**
49 * The constructor.
50 *
51 * @param[in] y the \e y coordinate.
52 * @param[in] x the \e x coordinate.
53 *
54 * \note the \e y coordinate is specified \e first.
55 * \warning either \e x or \e y can be infinite, but not both.
56 *
57 * The defaults (\e x = 1 and \e y = 0) are such that
58 * + no arguments gives an angle of 0;
59 * + 1 argument specifies the tangent of the angle.
60 **********************************************************************/
61 AuxAngle(real y = 0, real x = 1) : _y(y), _x(x) {}
62 /**
63 * @return the \e y component. This is the sine of the angle if the
64 * AuxAngle has been normalized.
65 **********************************************************************/
66 Math::real y() const { return _y; }
67 /**
68 * @return the \e x component. This is the cosine of the angle if the
69 * AuxAngle has been normalized.
70 **********************************************************************/
71 Math::real x() const { return _x; }
72 /**
73 * @return a reference to the \e y component. This allows this component
74 * to be altered.
75 **********************************************************************/
76 Math::real& y() { return _y; }
77 /**
78 * @return a reference to the \e x component. This allows this component
79 * to be altered.
80 **********************************************************************/
81 Math::real& x() { return _x; }
82 /**
83 * @return the AuxAngle converted to the conventional angle measured in
84 * degrees.
85 **********************************************************************/
86 Math::real degrees() const;
87 /**
88 * @return the AuxAngle converted to the conventional angle measured in
89 * radians.
90 **********************************************************************/
91 Math::real radians() const;
92 /**
93 * @return the lambertian of the AuxAngle.
94 *
95 * \note the lambertian of an angle &chi; is
96 * lam(&chi;) = asinh(tan(&chi;)).
97 **********************************************************************/
98 Math::real lam() const;
99 /**
100 * @return the lambertian of the AuxAngle in degrees.
101 *
102 * \note the lambertian of an angle &chi; is
103 * lam(&chi;) = asinh(tan(&chi;)).
104 **********************************************************************/
105 Math::real lamd() const;
106 /**
107 * @return the tangent of the angle.
108 **********************************************************************/
109 Math::real tan() const { return _y / _x; }
110 /**
111 * @return a new normalized AuxAngle with the point lying on the unit
112 * circle and the \e y and \e x components are equal to the sine and
113 * cosine of the angle.
114 **********************************************************************/
115 AuxAngle normalized() const;
116 /**
117 * Normalize the AuxAngle in place so that the \e y and \e x components are
118 * equal to the sine and cosine of the angle.
119 **********************************************************************/
120 void normalize() { *this = normalized(); }
121 /**
122 * Set the quadrant for the AuxAngle.
123 *
124 * @param[in] p the AuxAngle from which the quadrant information is taken.
125 * @return the new AuxAngle in the same quadrant as \e p.
126 **********************************************************************/
127 AuxAngle copyquadrant(const AuxAngle& p) const;
128 /**
129 * Add an AuxAngle.
130 *
131 * @param[in] p the AuxAngle to be added.
132 * @return a reference to the new AuxAngle.
133 *
134 * The addition is done in place, altering the current AuxAngle.
135 *
136 * \warning Neither *this nor \e p should have an infinite component. If
137 * necessary, invoke AuxAngle::normalize on these angles first.
138 **********************************************************************/
139 AuxAngle& operator+=(const AuxAngle& p);
140 /**
141 * Construct and return an AuxAngle specied as an angle in degrees.
142 *
143 * @param[in] d the angle measured in degrees.
144 * @return the corresponding AuxAngle.
145 *
146 * This allows a new AuxAngle to be initialized as an angle in degrees with
147 * @code
148 * AuxAngle phi(AuxAngle::degrees(d));
149 * @endcode
150 **********************************************************************/
151 static AuxAngle degrees(real d);
152 /**
153 * Construct and return an AuxAngle specied as an angle in radians.
154 *
155 * @param[in] r the angle measured in radians.
156 * @return the corresponding AuxAngle.
157 *
158 * This allows a new AuxAngle to be initialized as an angle in radians with
159 * @code
160 * AuxAngle phi(AuxAngle::radians(r));
161 * @endcode
162 **********************************************************************/
163 static AuxAngle radians(real r);
164 /**
165 * Construct and return an AuxAngle specied by the lambertian of the angle.
166 *
167 * @param[in] psi the lambertian of the angle.
168 * @return the corresponding AuxAngle.
169 *
170 * This allows a new AuxAngle to be initialized given the lambertian with
171 * @code
172 * AuxAngle chi(AuxAngle::lam(psi));
173 * @endcode
174 *
175 * \note this sets the angle &chi; to gd(&psi;) = atan(sinh(&psi;)).
176 **********************************************************************/
177 static AuxAngle lam(real psi);
178 /**
179 * Construct and return an AuxAngle specied by the lambertian of the angle
180 * in degrees.
181 *
182 * @param[in] psid the lambertian of the angle in degrees.
183 * @return the corresponding AuxAngle.
184 *
185 * This allows a new AuxAngle to be initialized given the lambertian with
186 * @code
187 * AuxAngle chi(AuxAngle::lamd(psid));
188 * @endcode
189 *
190 * \note this sets the angle &chi; to gd(&psi;) = atan(sinh(&psi;)).
191 **********************************************************************/
192 static AuxAngle lamd(real psid);
193 /**
194 * @return a "NaN" AuxAngle.
195 **********************************************************************/
196 static AuxAngle NaN();
197 };
198
200 real y, x;
201 Math::sincosd(d, y, x);
202 return AuxAngle(y, x);
203 }
204
206 using std::sin; using std::cos;
207 return AuxAngle(sin(r), cos(r));
208 }
209
210 inline AuxAngle AuxAngle::lam(real psi) {
211 using std::sinh;
212 return AuxAngle(sinh(psi));
213 }
214
215 inline AuxAngle AuxAngle::lamd(real psid) {
216 using std::sinh;
217 return AuxAngle(sinh(psid * Math::degree()));
218 }
219
221 return Math::atan2d(_y, _x);
222 }
223
225 using std::atan2; return atan2(_y, _x);
226 }
227
228 inline Math::real AuxAngle::lam() const {
229 using std::asinh; return asinh( tan() );
230 }
231
232 inline Math::real AuxAngle::lamd() const {
233 using std::asinh; return asinh( tan() ) / Math::degree();
234 }
235
236} // namespace GeographicLib
237
238#endif // GEOGRAPHICLIB_AUXANGLE_HPP
#define GEOGRAPHICLIB_EXPORT
Definition Constants.hpp:67
GeographicLib::Math::real real
Definition GeodSolve.cpp:31
Header for GeographicLib::Math class.
An accurate representation of angles.
Definition AuxAngle.hpp:43
Math::real y() const
Definition AuxAngle.hpp:66
Math::real x() const
Definition AuxAngle.hpp:71
Math::real radians() const
Definition AuxAngle.hpp:224
Math::real degrees() const
Definition AuxAngle.hpp:220
Math::real lamd() const
Definition AuxAngle.hpp:232
Math::real lam() const
Definition AuxAngle.hpp:228
Math::real tan() const
Definition AuxAngle.hpp:109
AuxAngle(real y=0, real x=1)
Definition AuxAngle.hpp:61
static T degree()
Definition Math.hpp:200
static void sincosd(T x, T &sinx, T &cosx)
Definition Math.cpp:106
static T atan2d(T y, T x)
Definition Math.cpp:183
Namespace for GeographicLib.