Commit | Line | Data |
5aabfad6 |
1 | #!./perl |
2 | |
3 | # |
4 | # Regression tests for the Math::Trig package |
5 | # |
bf5f1b4c |
6 | # The tests here are quite modest as the Math::Complex tests exercise |
7 | # these interfaces quite vigorously. |
5aabfad6 |
8 | # |
9 | # -- Jarkko Hietaniemi, April 1997 |
10 | |
11 | BEGIN { |
bf5f1b4c |
12 | if ($ENV{PERL_CORE}) { |
13 | chdir 't' if -d 't'; |
14 | @INC = '../lib'; |
15 | } |
5aabfad6 |
16 | } |
17 | |
affad850 |
18 | BEGIN { |
19 | eval { require Test::More }; |
20 | if ($@) { |
21 | # We are willing to lose testing in e.g. 5.00504. |
22 | print "1..0 # No Test::More, skipping\n"; |
23 | exit(0); |
24 | } else { |
25 | import Test::More; |
26 | } |
27 | } |
28 | |
29 | plan(tests => 69); |
30 | |
bf5f1b4c |
31 | use Math::Trig 1.03; |
32 | |
33 | my $pip2 = pi / 2; |
5aabfad6 |
34 | |
35 | use strict; |
36 | |
37 | use vars qw($x $y $z); |
38 | |
39 | my $eps = 1e-11; |
40 | |
2f367121 |
41 | if ($^O eq 'unicos') { # See lib/Math/Complex.pm and t/lib/complex.t. |
42 | $eps = 1e-10; |
43 | } |
44 | |
5aabfad6 |
45 | sub near ($$;$) { |
e64f0054 |
46 | my $e = defined $_[2] ? $_[2] : $eps; |
affad850 |
47 | my $d = $_[1] ? abs($_[0]/$_[1] - 1) : abs($_[0]); |
48 | print "# near? $_[0] $_[1] : $d : $e\n"; |
49 | $_[1] ? ($d < $e) : abs($_[0]) < $e; |
5aabfad6 |
50 | } |
51 | |
5aabfad6 |
52 | $x = 0.9; |
affad850 |
53 | ok(near(tan($x), sin($x) / cos($x))); |
5aabfad6 |
54 | |
affad850 |
55 | ok(near(sinh(2), 3.62686040784702)); |
5aabfad6 |
56 | |
affad850 |
57 | ok(near(acsch(0.1), 2.99822295029797)); |
5aabfad6 |
58 | |
59 | $x = asin(2); |
affad850 |
60 | is(ref $x, 'Math::Complex'); |
5aabfad6 |
61 | |
62 | # avoid using Math::Complex here |
63 | $x =~ /^([^-]+)(-[^i]+)i$/; |
64 | ($y, $z) = ($1, $2); |
affad850 |
65 | ok(near($y, 1.5707963267949)); |
66 | ok(near($z, -1.31695789692482)); |
5aabfad6 |
67 | |
affad850 |
68 | ok(near(deg2rad(90), pi/2)); |
5aabfad6 |
69 | |
affad850 |
70 | ok(near(rad2deg(pi), 180)); |
ace5de91 |
71 | |
d54bf66f |
72 | use Math::Trig ':radial'; |
73 | |
74 | { |
75 | my ($r,$t,$z) = cartesian_to_cylindrical(1,1,1); |
76 | |
affad850 |
77 | ok(near($r, sqrt(2))); |
78 | ok(near($t, deg2rad(45))); |
79 | ok(near($z, 1)); |
d54bf66f |
80 | |
81 | ($x,$y,$z) = cylindrical_to_cartesian($r, $t, $z); |
82 | |
affad850 |
83 | ok(near($x, 1)); |
84 | ok(near($y, 1)); |
85 | ok(near($z, 1)); |
d54bf66f |
86 | |
87 | ($r,$t,$z) = cartesian_to_cylindrical(1,1,0); |
88 | |
affad850 |
89 | ok(near($r, sqrt(2))); |
90 | ok(near($t, deg2rad(45))); |
91 | ok(near($z, 0)); |
d54bf66f |
92 | |
93 | ($x,$y,$z) = cylindrical_to_cartesian($r, $t, $z); |
94 | |
affad850 |
95 | ok(near($x, 1)); |
96 | ok(near($y, 1)); |
97 | ok(near($z, 0)); |
d54bf66f |
98 | } |
99 | |
100 | { |
101 | my ($r,$t,$f) = cartesian_to_spherical(1,1,1); |
102 | |
affad850 |
103 | ok(near($r, sqrt(3))); |
104 | ok(near($t, deg2rad(45))); |
105 | ok(near($f, atan2(sqrt(2), 1))); |
d54bf66f |
106 | |
107 | ($x,$y,$z) = spherical_to_cartesian($r, $t, $f); |
108 | |
affad850 |
109 | ok(near($x, 1)); |
110 | ok(near($y, 1)); |
111 | ok(near($z, 1)); |
112 | |
d54bf66f |
113 | ($r,$t,$f) = cartesian_to_spherical(1,1,0); |
114 | |
affad850 |
115 | ok(near($r, sqrt(2))); |
116 | ok(near($t, deg2rad(45))); |
117 | ok(near($f, deg2rad(90))); |
d54bf66f |
118 | |
119 | ($x,$y,$z) = spherical_to_cartesian($r, $t, $f); |
120 | |
affad850 |
121 | ok(near($x, 1)); |
122 | ok(near($y, 1)); |
123 | ok(near($z, 0)); |
d54bf66f |
124 | } |
125 | |
126 | { |
127 | my ($r,$t,$z) = cylindrical_to_spherical(spherical_to_cylindrical(1,1,1)); |
128 | |
affad850 |
129 | ok(near($r, 1)); |
130 | ok(near($t, 1)); |
131 | ok(near($z, 1)); |
d54bf66f |
132 | |
133 | ($r,$t,$z) = spherical_to_cylindrical(cylindrical_to_spherical(1,1,1)); |
134 | |
affad850 |
135 | ok(near($r, 1)); |
136 | ok(near($t, 1)); |
137 | ok(near($z, 1)); |
d54bf66f |
138 | } |
139 | |
140 | { |
9db5a202 |
141 | use Math::Trig 'great_circle_distance'; |
d54bf66f |
142 | |
affad850 |
143 | ok(near(great_circle_distance(0, 0, 0, pi/2), pi/2)); |
d54bf66f |
144 | |
affad850 |
145 | ok(near(great_circle_distance(0, 0, pi, pi), pi)); |
d54bf66f |
146 | |
9db5a202 |
147 | # London to Tokyo. |
148 | my @L = (deg2rad(-0.5), deg2rad(90 - 51.3)); |
149 | my @T = (deg2rad(139.8),deg2rad(90 - 35.7)); |
d54bf66f |
150 | |
9db5a202 |
151 | my $km = great_circle_distance(@L, @T, 6378); |
d54bf66f |
152 | |
affad850 |
153 | ok(near($km, 9605.26637021388)); |
9db5a202 |
154 | } |
155 | |
156 | { |
fdf27e67 |
157 | my $R2D = 57.295779513082320876798154814169; |
158 | |
159 | sub frac { $_[0] - int($_[0]) } |
160 | |
9db5a202 |
161 | my $lotta_radians = deg2rad(1E+20, 1); |
affad850 |
162 | ok(near($lotta_radians, 1E+20/$R2D)); |
9db5a202 |
163 | |
164 | my $negat_degrees = rad2deg(-1E20, 1); |
affad850 |
165 | ok(near($negat_degrees, -1E+20*$R2D)); |
9db5a202 |
166 | |
167 | my $posit_degrees = rad2deg(-10000, 1); |
affad850 |
168 | ok(near($posit_degrees, -10000*$R2D)); |
d54bf66f |
169 | } |
170 | |
7e5f197a |
171 | { |
172 | use Math::Trig 'great_circle_direction'; |
173 | |
affad850 |
174 | ok(near(great_circle_direction(0, 0, 0, pi/2), pi)); |
7e5f197a |
175 | |
bf5f1b4c |
176 | # Retired test: Relies on atan2(0, 0), which is not portable. |
affad850 |
177 | # ok(near(great_circle_direction(0, 0, pi, pi), -pi()/2)); |
7e5f197a |
178 | |
d139edd6 |
179 | my @London = (deg2rad( -0.167), deg2rad(90 - 51.3)); |
180 | my @Tokyo = (deg2rad( 139.5), deg2rad(90 - 35.7)); |
181 | my @Berlin = (deg2rad ( 13.417), deg2rad(90 - 52.533)); |
182 | my @Paris = (deg2rad ( 2.333), deg2rad(90 - 48.867)); |
7e5f197a |
183 | |
affad850 |
184 | ok(near(rad2deg(great_circle_direction(@London, @Tokyo)), |
185 | 31.791945393073)); |
bf5f1b4c |
186 | |
affad850 |
187 | ok(near(rad2deg(great_circle_direction(@Tokyo, @London)), |
188 | 336.069766430326)); |
d139edd6 |
189 | |
affad850 |
190 | ok(near(rad2deg(great_circle_direction(@Berlin, @Paris)), |
191 | 246.800348034667)); |
d139edd6 |
192 | |
affad850 |
193 | ok(near(rad2deg(great_circle_direction(@Paris, @Berlin)), |
194 | 58.2079877553156)); |
bf5f1b4c |
195 | |
196 | use Math::Trig 'great_circle_bearing'; |
197 | |
affad850 |
198 | ok(near(rad2deg(great_circle_bearing(@Paris, @Berlin)), |
199 | 58.2079877553156)); |
bf5f1b4c |
200 | |
201 | use Math::Trig 'great_circle_waypoint'; |
202 | use Math::Trig 'great_circle_midpoint'; |
203 | |
204 | my ($lon, $lat); |
205 | |
206 | ($lon, $lat) = great_circle_waypoint(@London, @Tokyo, 0.0); |
207 | |
affad850 |
208 | ok(near($lon, $London[0])); |
bf5f1b4c |
209 | |
618e05e9 |
210 | ok(near($lat, $London[1])); |
bf5f1b4c |
211 | |
212 | ($lon, $lat) = great_circle_waypoint(@London, @Tokyo, 1.0); |
213 | |
affad850 |
214 | ok(near($lon, $Tokyo[0])); |
bf5f1b4c |
215 | |
618e05e9 |
216 | ok(near($lat, $Tokyo[1])); |
bf5f1b4c |
217 | |
218 | ($lon, $lat) = great_circle_waypoint(@London, @Tokyo, 0.5); |
219 | |
618e05e9 |
220 | ok(near($lon, 1.55609593577679)); # 89.16 E |
bf5f1b4c |
221 | |
618e05e9 |
222 | ok(near($lat, 0.36783532946162)); # 68.93 N |
bf5f1b4c |
223 | |
224 | ($lon, $lat) = great_circle_midpoint(@London, @Tokyo); |
225 | |
618e05e9 |
226 | ok(near($lon, 1.55609593577679)); # 89.16 E |
bf5f1b4c |
227 | |
618e05e9 |
228 | ok(near($lat, 0.367835329461615)); # 68.93 N |
bf5f1b4c |
229 | |
230 | ($lon, $lat) = great_circle_waypoint(@London, @Tokyo, 0.25); |
231 | |
618e05e9 |
232 | ok(near($lon, 0.516073562850837)); # 29.57 E |
affad850 |
233 | |
618e05e9 |
234 | ok(near($lat, 0.400231313403387)); # 67.07 N |
bf5f1b4c |
235 | |
bf5f1b4c |
236 | ($lon, $lat) = great_circle_waypoint(@London, @Tokyo, 0.75); |
237 | |
618e05e9 |
238 | ok(near($lon, 2.17494903805952)); # 124.62 E |
bf5f1b4c |
239 | |
618e05e9 |
240 | ok(near($lat, 0.617809294053591)); # 54.60 N |
bf5f1b4c |
241 | |
242 | use Math::Trig 'great_circle_destination'; |
243 | |
244 | my $dir1 = great_circle_direction(@London, @Tokyo); |
245 | my $dst1 = great_circle_distance(@London, @Tokyo); |
246 | |
247 | ($lon, $lat) = great_circle_destination(@London, $dir1, $dst1); |
248 | |
affad850 |
249 | ok(near($lon, $Tokyo[0])); |
bf5f1b4c |
250 | |
affad850 |
251 | ok(near($lat, $pip2 - $Tokyo[1])); |
bf5f1b4c |
252 | |
253 | my $dir2 = great_circle_direction(@Tokyo, @London); |
254 | my $dst2 = great_circle_distance(@Tokyo, @London); |
255 | |
256 | ($lon, $lat) = great_circle_destination(@Tokyo, $dir2, $dst2); |
257 | |
affad850 |
258 | ok(near($lon, $London[0])); |
bf5f1b4c |
259 | |
affad850 |
260 | ok(near($lat, $pip2 - $London[1])); |
bf5f1b4c |
261 | |
262 | my $dir3 = (great_circle_destination(@London, $dir1, $dst1))[2]; |
263 | |
affad850 |
264 | ok(near($dir3, 2.69379263839118)); # about 154.343 deg |
bf5f1b4c |
265 | |
266 | my $dir4 = (great_circle_destination(@Tokyo, $dir2, $dst2))[2]; |
267 | |
affad850 |
268 | ok(near($dir4, 3.6993902625701)); # about 211.959 deg |
bf5f1b4c |
269 | |
affad850 |
270 | ok(near($dst1, $dst2)); |
7e5f197a |
271 | } |
272 | |
5aabfad6 |
273 | # eof |