line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
1
|
|
|
|
|
|
|
package Astro::Utils; |
2
|
|
|
|
|
|
|
|
3
|
|
|
|
|
|
|
$Astro::Utils::VERSION = '0.04'; |
4
|
|
|
|
|
|
|
$Astro::Utils::AUTHORITY = 'cpan:MANWAR'; |
5
|
|
|
|
|
|
|
|
6
|
|
|
|
|
|
|
=head1 NAME |
7
|
|
|
|
|
|
|
|
8
|
|
|
|
|
|
|
Astro::Utils - Utility package for Astronomical Calculations. |
9
|
|
|
|
|
|
|
|
10
|
|
|
|
|
|
|
=head1 VERSION |
11
|
|
|
|
|
|
|
|
12
|
|
|
|
|
|
|
Version 0.04 |
13
|
|
|
|
|
|
|
|
14
|
|
|
|
|
|
|
=cut |
15
|
|
|
|
|
|
|
|
16
|
3
|
|
|
3
|
|
216281
|
use vars qw(@ISA @EXPORT); |
|
3
|
|
|
|
|
27
|
|
|
3
|
|
|
|
|
194
|
|
17
|
|
|
|
|
|
|
require Exporter; |
18
|
|
|
|
|
|
|
@ISA = qw(Exporter); |
19
|
|
|
|
|
|
|
@EXPORT = qw(calculate_equinox calculate_solstice); |
20
|
|
|
|
|
|
|
|
21
|
3
|
|
|
3
|
|
54
|
use 5.006; |
|
3
|
|
|
|
|
9
|
|
22
|
3
|
|
|
3
|
|
13
|
use strict; use warnings; |
|
3
|
|
|
3
|
|
9
|
|
|
3
|
|
|
|
|
49
|
|
|
3
|
|
|
|
|
10
|
|
|
3
|
|
|
|
|
3
|
|
|
3
|
|
|
|
|
88
|
|
23
|
3
|
|
|
3
|
|
1043
|
use Data::Dumper; |
|
3
|
|
|
|
|
14889
|
|
|
3
|
|
|
|
|
176
|
|
24
|
3
|
|
|
3
|
|
1648
|
use DateTime; |
|
3
|
|
|
|
|
1382302
|
|
|
3
|
|
|
|
|
4404
|
|
25
|
|
|
|
|
|
|
|
26
|
|
|
|
|
|
|
my $PI = 3.141592653589793; |
27
|
|
|
|
|
|
|
my $TYPE = { 'MAR' => 0, 'JUN' => 1, 'SEP' => 2, 'DEC' => 3 }; |
28
|
|
|
|
|
|
|
|
29
|
|
|
|
|
|
|
=head1 DESCRIPTION |
30
|
|
|
|
|
|
|
|
31
|
|
|
|
|
|
|
The entire algorithm is based on the book "Astronomical Algorithms", 2nd Edition |
32
|
|
|
|
|
|
|
by Jean Meeus,(C)1998, published by Willmann-Bell, Inc. I needed this for one of |
33
|
|
|
|
|
|
|
my package L<Calendar::Bahai>. |
34
|
|
|
|
|
|
|
|
35
|
|
|
|
|
|
|
The calculated times are in Terrestrial Dynamical Time (TDT or TT), a replacement |
36
|
|
|
|
|
|
|
for Ephemeris Times(ET).TDT is a uniform time used for astronomical calculations. |
37
|
|
|
|
|
|
|
|
38
|
|
|
|
|
|
|
=head1 SYNOPSIS |
39
|
|
|
|
|
|
|
|
40
|
|
|
|
|
|
|
use strict; use warnings; |
41
|
|
|
|
|
|
|
use Astro::Utils; |
42
|
|
|
|
|
|
|
|
43
|
|
|
|
|
|
|
print "Mar'2015 Equinox (UTC): ", calculate_equinox ('mar', 'utc', 2015),"\n"; |
44
|
|
|
|
|
|
|
print "Mar'2015 Equinox (TDT): ", calculate_equinox ('mar', 'tdt', 2015),"\n"; |
45
|
|
|
|
|
|
|
|
46
|
|
|
|
|
|
|
print "Jun'2015 Solstice (UTC): ", calculate_solstice('jun', 'utc', 2015),"\n"; |
47
|
|
|
|
|
|
|
print "Jun'2015 Solstice (TDT): ", calculate_solstice('jun', 'tdt', 2015),"\n"; |
48
|
|
|
|
|
|
|
|
49
|
|
|
|
|
|
|
print "Sep'2015 Equinox (UTC): ", calculate_equinox ('sep', 'utc', 2015),"\n"; |
50
|
|
|
|
|
|
|
print "Sep'2015 Equinox (TDT): ", calculate_equinox ('sep', 'tdt', 2015),"\n"; |
51
|
|
|
|
|
|
|
|
52
|
|
|
|
|
|
|
print "Dec'2015 Solstice (UTC): ", calculate_solstice('dec', 'utc', 2015),"\n"; |
53
|
|
|
|
|
|
|
print "Dec'2015 Solstice (TDT): ", calculate_solstice('dec', 'tdt', 2015),"\n"; |
54
|
|
|
|
|
|
|
|
55
|
|
|
|
|
|
|
=head1 METHODS |
56
|
|
|
|
|
|
|
|
57
|
|
|
|
|
|
|
=head2 calculate_equinox($type, $timezone, $year) |
58
|
|
|
|
|
|
|
|
59
|
|
|
|
|
|
|
The param C<$type> can be either 'mar' or 'sep'. The param C<$timezone> can be |
60
|
|
|
|
|
|
|
either 'UTC' or 'TDT'. And finally C<$year> can be anything between -1000 & 3000. |
61
|
|
|
|
|
|
|
All parameters are required. |
62
|
|
|
|
|
|
|
|
63
|
|
|
|
|
|
|
=cut |
64
|
|
|
|
|
|
|
|
65
|
|
|
|
|
|
|
sub calculate_equinox { |
66
|
4
|
|
|
4
|
1
|
1687
|
my ($type, $timezone, $year) = @_; |
67
|
|
|
|
|
|
|
|
68
|
4
|
50
|
33
|
|
|
38
|
die "ERROR: Year should be between -1000 and 3000.\n" |
|
|
|
33
|
|
|
|
|
69
|
|
|
|
|
|
|
unless (defined $year && ($year >= -1000) && ($year <= 3000)); |
70
|
|
|
|
|
|
|
|
71
|
4
|
100
|
|
|
|
28
|
if ($timezone =~ /^utc$/i) { |
|
|
50
|
|
|
|
|
|
72
|
2
|
|
|
|
|
14
|
return _calc_utc_equinox($TYPE->{uc($type)}, $year); |
73
|
|
|
|
|
|
|
} |
74
|
|
|
|
|
|
|
elsif ($timezone =~ /^tdt$/i) { |
75
|
2
|
|
|
|
|
10
|
return _calc_tdt_equinox($TYPE->{uc($type)}, $year); |
76
|
|
|
|
|
|
|
} |
77
|
|
|
|
|
|
|
else { |
78
|
0
|
|
|
|
|
0
|
die "ERROR: Invalid timezone [$timezone] received.\n"; |
79
|
|
|
|
|
|
|
} |
80
|
|
|
|
|
|
|
} |
81
|
|
|
|
|
|
|
|
82
|
|
|
|
|
|
|
=head2 calculate_solstice($type. $timezone, $year) |
83
|
|
|
|
|
|
|
|
84
|
|
|
|
|
|
|
The param C<$type> can be either 'jun' or 'dec'. The param C<$timezone> can be |
85
|
|
|
|
|
|
|
either 'UTC' or 'TDT'. And finally C<$year> can be anything between -1000 & 3000. |
86
|
|
|
|
|
|
|
All parameters are required. |
87
|
|
|
|
|
|
|
|
88
|
|
|
|
|
|
|
=cut |
89
|
|
|
|
|
|
|
|
90
|
|
|
|
|
|
|
sub calculate_solstice { |
91
|
4
|
|
|
4
|
1
|
1515
|
my ($type, $timezone, $year) = @_; |
92
|
|
|
|
|
|
|
|
93
|
4
|
50
|
33
|
|
|
36
|
die "ERROR: Year should be between -1000 and 3000.\n" |
|
|
|
33
|
|
|
|
|
94
|
|
|
|
|
|
|
unless (defined $year && ($year >= -1000) && ($year <= 3000)); |
95
|
|
|
|
|
|
|
|
96
|
4
|
100
|
|
|
|
28
|
if ($timezone =~ /^utc$/i) { |
|
|
50
|
|
|
|
|
|
97
|
2
|
|
|
|
|
14
|
return _calc_utc_solstice($TYPE->{uc($type)}, $year); |
98
|
|
|
|
|
|
|
} |
99
|
|
|
|
|
|
|
elsif ($timezone =~ /^tdt$/i) { |
100
|
2
|
|
|
|
|
9
|
return _calc_tdt_solstice($TYPE->{uc($type)}, $year); |
101
|
|
|
|
|
|
|
} |
102
|
|
|
|
|
|
|
else { |
103
|
0
|
|
|
|
|
0
|
die "ERROR: Invalid timezone [$timezone] received.\n"; |
104
|
|
|
|
|
|
|
} |
105
|
|
|
|
|
|
|
} |
106
|
|
|
|
|
|
|
|
107
|
|
|
|
|
|
|
# |
108
|
|
|
|
|
|
|
# |
109
|
|
|
|
|
|
|
# PRIVATE METHODS |
110
|
|
|
|
|
|
|
|
111
|
|
|
|
|
|
|
sub _calc_utc_equinox { |
112
|
2
|
|
|
2
|
|
7
|
my ($k, $year) = @_; |
113
|
|
|
|
|
|
|
|
114
|
2
|
50
|
33
|
|
|
19
|
die "ERROR: Invalid type for equinox.\n" unless (defined $k && ($k =~ /^[0|2]$/)); |
115
|
2
|
|
|
|
|
20
|
my $jd = _calc_jd($k, $year); |
116
|
2
|
|
|
|
|
9
|
return _jd_to_utc($jd); |
117
|
|
|
|
|
|
|
} |
118
|
|
|
|
|
|
|
|
119
|
|
|
|
|
|
|
sub _calc_utc_solstice { |
120
|
2
|
|
|
2
|
|
9
|
my ($k, $year) = @_; |
121
|
|
|
|
|
|
|
|
122
|
2
|
50
|
33
|
|
|
19
|
die "ERROR: Invalid type for solstice.\n" unless (defined $k && ($k =~ /^[1|3]$/)); |
123
|
2
|
|
|
|
|
25
|
my $jd = _calc_jd($k, $year); |
124
|
2
|
|
|
|
|
9
|
return _jd_to_utc($jd); |
125
|
|
|
|
|
|
|
} |
126
|
|
|
|
|
|
|
|
127
|
|
|
|
|
|
|
sub _calc_tdt_equinox { |
128
|
2
|
|
|
2
|
|
5
|
my ($k, $year) = @_; |
129
|
|
|
|
|
|
|
|
130
|
2
|
50
|
33
|
|
|
15
|
die "ERROR: Invalid type for equinox.\n" unless (defined $k && ($k =~ /^[0|2]$/)); |
131
|
2
|
|
|
|
|
5
|
my $jd = _calc_jd($k, $year); |
132
|
2
|
|
|
|
|
5
|
return _jd_to_tdt($jd); |
133
|
|
|
|
|
|
|
} |
134
|
|
|
|
|
|
|
|
135
|
|
|
|
|
|
|
sub _calc_tdt_solstice { |
136
|
2
|
|
|
2
|
|
4
|
my ($k, $year) = @_; |
137
|
|
|
|
|
|
|
|
138
|
2
|
50
|
33
|
|
|
12
|
die "ERROR: Invalid type for solstice.\n" unless (defined $k && ($k =~ /^[1|3]$/)); |
139
|
2
|
|
|
|
|
6
|
my $jd = _calc_jd($k, $year); |
140
|
2
|
|
|
|
|
5
|
return _jd_to_tdt($jd); |
141
|
|
|
|
|
|
|
} |
142
|
|
|
|
|
|
|
|
143
|
|
|
|
|
|
|
sub _calc_jd { |
144
|
8
|
|
|
8
|
|
23
|
my ($k, $year) = @_; |
145
|
|
|
|
|
|
|
|
146
|
|
|
|
|
|
|
# Astronmical Algorithms, Chapter 27. |
147
|
8
|
|
|
|
|
30
|
my $jde0 = _jde0($k, $year); |
148
|
8
|
|
|
|
|
21
|
my $t = ($jde0 - 2451545.0) / 36525; |
149
|
8
|
|
|
|
|
14
|
my $w = 35999.373 * $t - 2.47; |
150
|
8
|
|
|
|
|
19
|
my $dl = 1 + 0.0334 * _cos($w) + 0.0007 * _cos(2 * $w); |
151
|
8
|
|
|
|
|
22
|
my $s = _periodic_term_24($t); |
152
|
|
|
|
|
|
|
|
153
|
8
|
|
|
|
|
25
|
return ($jde0 + ( (0.00001 * $s) / $dl )); |
154
|
|
|
|
|
|
|
} |
155
|
|
|
|
|
|
|
|
156
|
|
|
|
|
|
|
sub _jd_to_utc { |
157
|
4
|
|
|
4
|
|
11
|
my ($jd) = @_; |
158
|
|
|
|
|
|
|
|
159
|
4
|
|
|
|
|
15
|
my ($yr, $mon, $day, $hr, $min, $sec) = _process($jd); |
160
|
|
|
|
|
|
|
|
161
|
4
|
|
|
|
|
34
|
my $date = DateTime->new(year => $yr, month => $mon, day => $day, hour => $hr, minute => $min, second => $sec); |
162
|
|
|
|
|
|
|
|
163
|
|
|
|
|
|
|
# Astronmical Algorithms, Chapter 10, page 79 (Table 10.A). |
164
|
4
|
|
|
|
|
1783
|
my $first = 1620; |
165
|
4
|
|
|
|
|
9
|
my $last = 2002; |
166
|
4
|
|
|
|
|
123
|
my @tbl = (121,112,103,95,88,82,77,72,68,63,60,56,53,51,48,46,44,42,40,38, # 1620 |
167
|
|
|
|
|
|
|
35,33,31,29,26,24,22,20,18,16,14,12,11,10,9,8,7,7,7,7, # 1660 |
168
|
|
|
|
|
|
|
7,7,8,8,9,9,9,9,9,10,10,10,10,10,10,10,10,11,11,11, # 1700 |
169
|
|
|
|
|
|
|
11,11,12,12,12,12,13,13,13,14,14,14,14,15,15,15,15,15,16,16, # 1740 |
170
|
|
|
|
|
|
|
16,16,16,16,16,16,15,15,14,13, # 1780 |
171
|
|
|
|
|
|
|
13.1,12.5,12.2,12.0,12.0,12.0,12.0,12.0,12.0,11.9,11.6,11.0,10.2,9.2,8.2, # 1800 |
172
|
|
|
|
|
|
|
7.1,6.2,5.6,5.4,5.3,5.4,5.6,5.9,6.2,6.5,6.8,7.1,7.3,7.5,7.6, # 1830 |
173
|
|
|
|
|
|
|
7.7,7.3,6.2,5.2,2.7,1.4,-1.2,-2.8,-3.8,-4.8,-5.5,-5.3,-5.6,-5.7,-5.9, # 1860 |
174
|
|
|
|
|
|
|
-6.0,-6.3,-6.5,-6.2,-4.7,-2.8,-0.1,2.6,5.3,7.7,10.4,13.3,16.0,18.2,20.2, # 1890 |
175
|
|
|
|
|
|
|
21.1,22.4,23.5,23.8,24.3,24.0,23.9,23.9,23.7,24.0,24.3,25.3,26.2,27.3,28.2, # 1920 |
176
|
|
|
|
|
|
|
29.1,30.0,30.7,31.4,32.2,33.1,34.0,35.0,36.5,38.3,40.2,42.2,44.5,46.5,48.5, # 1950 |
177
|
|
|
|
|
|
|
50.5,52.5,53.8,54.9,55.8,56.9,58.3,60.0,61.6,63.0,63.8,64.3 # 1980, 2002 last entry |
178
|
|
|
|
|
|
|
); |
179
|
|
|
|
|
|
|
|
180
|
4
|
|
|
|
|
11
|
my $delta_t = 0; |
181
|
4
|
|
|
|
|
14
|
my $t = ($yr - 2000) / 100; |
182
|
|
|
|
|
|
|
|
183
|
4
|
50
|
33
|
|
|
29
|
if ($yr >= $first && $yr <= $last) { |
|
|
0
|
|
|
|
|
|
|
|
0
|
|
|
|
|
|
184
|
4
|
50
|
|
|
|
15
|
if ($yr % 2) { |
185
|
0
|
|
|
|
|
0
|
$delta_t = ($tbl[($yr - $first - 1) / 2] + $tbl[($yr - $first + 1) / 2] ) / 2; |
186
|
|
|
|
|
|
|
} |
187
|
|
|
|
|
|
|
else { |
188
|
4
|
|
|
|
|
14
|
$delta_t = $tbl[($yr - $first) / 2]; |
189
|
|
|
|
|
|
|
} |
190
|
|
|
|
|
|
|
} elsif ($yr < 948) { |
191
|
0
|
|
|
|
|
0
|
$delta_t = 2177 + 497 * $t + (44.1 * _pow($t, 2)); |
192
|
|
|
|
|
|
|
} elsif ($yr >= 948) { |
193
|
0
|
|
|
|
|
0
|
$delta_t = 102 + 102 * $t + (25.3 * _pow($t, 2)); |
194
|
0
|
0
|
0
|
|
|
0
|
if ($yr >= 2000 && $yr <= 2100) { |
195
|
0
|
|
|
|
|
0
|
$delta_t += 0.37 * ($yr - 2100); |
196
|
|
|
|
|
|
|
} |
197
|
|
|
|
|
|
|
} |
198
|
|
|
|
|
|
|
|
199
|
4
|
|
|
|
|
21
|
$date->subtract(seconds => $delta_t); |
200
|
|
|
|
|
|
|
|
201
|
4
|
|
|
|
|
6058
|
return sprintf("%04d-%02d-%02d %02d:%02d:%02d", |
202
|
|
|
|
|
|
|
$date->year, $date->month, $date->day, $date->hour, $date->minute, $date->second); |
203
|
|
|
|
|
|
|
} |
204
|
|
|
|
|
|
|
|
205
|
|
|
|
|
|
|
sub _jd_to_tdt { |
206
|
4
|
|
|
4
|
|
8
|
my ($jd) = @_; |
207
|
|
|
|
|
|
|
|
208
|
4
|
|
|
|
|
9
|
my ($yr, $mon, $day, $hr, $min, $sec) = _process($jd); |
209
|
4
|
|
|
|
|
36
|
return sprintf("%04d-%02d-%02d %02d:%02d:%02d", $yr, $mon, $day, $hr, $min, $sec); |
210
|
|
|
|
|
|
|
} |
211
|
|
|
|
|
|
|
|
212
|
|
|
|
|
|
|
sub _process { |
213
|
8
|
|
|
8
|
|
16
|
my ($jd) = @_; |
214
|
|
|
|
|
|
|
|
215
|
|
|
|
|
|
|
# Astronmical Algorithms Chapter 7, page 63. |
216
|
8
|
|
|
|
|
15
|
my ($a, $alpha); |
217
|
8
|
|
|
|
|
22
|
my $z = int($jd + 0.5); |
218
|
8
|
|
|
|
|
18
|
my $f = ($jd + 0.5) - $z; |
219
|
|
|
|
|
|
|
|
220
|
8
|
50
|
|
|
|
24
|
if ($z < 2299161) { |
221
|
0
|
|
|
|
|
0
|
$a = $z; |
222
|
|
|
|
|
|
|
} |
223
|
|
|
|
|
|
|
else { |
224
|
8
|
|
|
|
|
20
|
$alpha = int(($z - 1867216.25) / 36524.25); |
225
|
8
|
|
|
|
|
21
|
$a = $z + 1 + $alpha - int($alpha / 4); |
226
|
|
|
|
|
|
|
} |
227
|
|
|
|
|
|
|
|
228
|
8
|
|
|
|
|
13
|
my $b = $a + 1524; |
229
|
8
|
|
|
|
|
14
|
my $c = int(($b - 122.1) / 365.25); |
230
|
8
|
|
|
|
|
18
|
my $d = int(365.25 * $c); |
231
|
8
|
|
|
|
|
15
|
my $e = int(($b -$d) / 30.6001); |
232
|
8
|
|
|
|
|
23
|
my $dt = $b - $d - int(30.6001 * $e) + $f; |
233
|
8
|
50
|
|
|
|
21
|
my $mon = $e - (($e < 13.5)?(1):(13)); |
234
|
8
|
50
|
|
|
|
22
|
my $yr = $c - (($mon > 2.5)?(4716):(4715)); |
235
|
8
|
|
|
|
|
15
|
my $day = int($dt); |
236
|
8
|
|
|
|
|
14
|
my $h = 24 * ($dt - $day); |
237
|
8
|
|
|
|
|
13
|
my $hr = int($h); |
238
|
8
|
|
|
|
|
21
|
my $m = 60 * ($h - $hr); |
239
|
8
|
|
|
|
|
13
|
my $min = int($m); |
240
|
8
|
|
|
|
|
21
|
my $sec = int(60 * ($m - $min)); |
241
|
|
|
|
|
|
|
|
242
|
8
|
|
|
|
|
28
|
return ($yr, $mon, $day, $hr, $min, $sec); |
243
|
|
|
|
|
|
|
} |
244
|
|
|
|
|
|
|
|
245
|
|
|
|
|
|
|
sub _periodic_term_24 { |
246
|
8
|
|
|
8
|
|
14
|
my ($t) = @_; |
247
|
|
|
|
|
|
|
|
248
|
|
|
|
|
|
|
# Astronmical Algorithms, Chapter 27, page 179 (Table 27.C). |
249
|
8
|
|
|
|
|
30
|
my @a = (485,203,199,182,156,136,77,74,70,58,52, |
250
|
|
|
|
|
|
|
50,45,44,29,18,17,16,14,12,12,12,9,8); |
251
|
8
|
|
|
|
|
24
|
my @b = (324.96,337.23,342.08,27.85,73.14,171.52, |
252
|
|
|
|
|
|
|
222.54,296.72,243.58,119.81,297.17,21.02, |
253
|
|
|
|
|
|
|
247.54,325.15,60.93,155.12,288.79,198.04, |
254
|
|
|
|
|
|
|
199.76,95.39,287.11,320.81,227.73,15.45); |
255
|
8
|
|
|
|
|
23
|
my @c = (1934.136,32964.467,20.186,445267.112,45036.886, |
256
|
|
|
|
|
|
|
22518.443,65928.934,3034.906,9037.513, |
257
|
|
|
|
|
|
|
33718.147,150.678,2281.226,29929.562,31555.956, |
258
|
|
|
|
|
|
|
4443.417,67555.328,4562.452,62894.029, |
259
|
|
|
|
|
|
|
31436.921,14577.848,31931.756,34777.259, |
260
|
|
|
|
|
|
|
1222.114,16859.074); |
261
|
|
|
|
|
|
|
|
262
|
8
|
|
|
|
|
13
|
my $s = 0; |
263
|
8
|
|
|
|
|
16
|
foreach my $i (0..23) { |
264
|
192
|
|
|
|
|
337
|
$s += ($a[$i] * _cos($b[$i] + ($c[$i] * $t))); |
265
|
|
|
|
|
|
|
} |
266
|
|
|
|
|
|
|
|
267
|
8
|
|
|
|
|
33
|
return $s; |
268
|
|
|
|
|
|
|
} |
269
|
|
|
|
|
|
|
|
270
|
|
|
|
|
|
|
sub _jde0 { |
271
|
8
|
|
|
8
|
|
21
|
my ($k, $year) = @_; |
272
|
|
|
|
|
|
|
|
273
|
|
|
|
|
|
|
# Julian Ephemeris Day Calculation. |
274
|
8
|
|
|
|
|
20
|
my ($jde0, $y); |
275
|
|
|
|
|
|
|
|
276
|
8
|
50
|
33
|
|
|
79
|
if ($year >= -1000 && $year <= 1000) { |
|
|
50
|
33
|
|
|
|
|
277
|
|
|
|
|
|
|
# Astronmical Algorithms, Chapter 27, page 178 (Table 27.A). |
278
|
0
|
|
|
|
|
0
|
$y = $year / 1000; |
279
|
|
|
|
|
|
|
|
280
|
0
|
0
|
|
|
|
0
|
if ($k == 0) { |
|
|
0
|
|
|
|
|
|
|
|
0
|
|
|
|
|
|
|
|
0
|
|
|
|
|
|
281
|
0
|
|
|
|
|
0
|
$jde0 = 1721139.29189 + |
282
|
|
|
|
|
|
|
(365242.13740 * $y) + |
283
|
|
|
|
|
|
|
(0.06134 * _pow($y, 2)) + |
284
|
|
|
|
|
|
|
(0.00111 * _pow($y, 3)) - |
285
|
|
|
|
|
|
|
(0.00071 * _pow($y, 4)); |
286
|
|
|
|
|
|
|
} |
287
|
|
|
|
|
|
|
elsif ($k == 1) { |
288
|
0
|
|
|
|
|
0
|
$jde0 = 1721233.25401 + |
289
|
|
|
|
|
|
|
(365241.72562 * $y) - |
290
|
|
|
|
|
|
|
(0.05323 * _pow($y, 2)) + |
291
|
|
|
|
|
|
|
(0.00907 * _pow($y, 3)) + |
292
|
|
|
|
|
|
|
(0.00025 * _pow($y, 4)); |
293
|
|
|
|
|
|
|
} |
294
|
|
|
|
|
|
|
elsif ($k == 2) { |
295
|
0
|
|
|
|
|
0
|
$jde0 = 1721325.70455 + |
296
|
|
|
|
|
|
|
(365242.49558 * $y) - |
297
|
|
|
|
|
|
|
(0.11677 * _pow($y, 2)) - |
298
|
|
|
|
|
|
|
(0.00297 * _pow($y, 3)) + |
299
|
|
|
|
|
|
|
(0.00074 * _pow($y, 4)); |
300
|
|
|
|
|
|
|
} |
301
|
|
|
|
|
|
|
elsif ($k == 3) { |
302
|
0
|
|
|
|
|
0
|
$jde0 = 1721414.39987 + |
303
|
|
|
|
|
|
|
(365242.88257 * $y) - |
304
|
|
|
|
|
|
|
(0.00769 * _pow($y, 2)) - |
305
|
|
|
|
|
|
|
(0.00933 * _pow($y, 3)) - |
306
|
|
|
|
|
|
|
(0.00006 * _pow($y, 4)); |
307
|
|
|
|
|
|
|
} |
308
|
|
|
|
|
|
|
} |
309
|
|
|
|
|
|
|
elsif ($year > 1000 && $year <= 3000) { |
310
|
|
|
|
|
|
|
# Astronmical Algorithms, Chapter 27, page 178 (Table 27.B). |
311
|
8
|
|
|
|
|
28
|
$y = ($year - 2000) / 1000; |
312
|
|
|
|
|
|
|
|
313
|
8
|
100
|
|
|
|
42
|
if ($k == 0) { |
|
|
100
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
|
50
|
|
|
|
|
|
314
|
2
|
|
|
|
|
8
|
$jde0 = 2451623.80984 + |
315
|
|
|
|
|
|
|
(365242.37404 * $y) + |
316
|
|
|
|
|
|
|
(0.05169 * _pow($y, 2)) - |
317
|
|
|
|
|
|
|
(0.00411 * _pow($y, 3)) - |
318
|
|
|
|
|
|
|
(0.00057 * _pow($y, 4)); |
319
|
|
|
|
|
|
|
} |
320
|
|
|
|
|
|
|
elsif ($k == 1) { |
321
|
2
|
|
|
|
|
9
|
$jde0 = 2451716.56767 + |
322
|
|
|
|
|
|
|
(365241.62603 * $y) + |
323
|
|
|
|
|
|
|
(0.00325 * _pow($y, 2)) + |
324
|
|
|
|
|
|
|
(0.00888 * _pow($y, 3)) - |
325
|
|
|
|
|
|
|
(0.00030 * _pow($y, 4)); |
326
|
|
|
|
|
|
|
} |
327
|
|
|
|
|
|
|
elsif ($k == 2) { |
328
|
2
|
|
|
|
|
9
|
$jde0 = 2451810.21715 + |
329
|
|
|
|
|
|
|
(365242.01767 * $y) - |
330
|
|
|
|
|
|
|
(0.11575 * _pow($y, 2)) + |
331
|
|
|
|
|
|
|
(0.00337 * _pow($y, 3)) + |
332
|
|
|
|
|
|
|
(0.00078 * _pow($y, 4)); |
333
|
|
|
|
|
|
|
} |
334
|
|
|
|
|
|
|
elsif ($k == 3) { |
335
|
2
|
|
|
|
|
7
|
$jde0 = 2451900.05952 + |
336
|
|
|
|
|
|
|
(365242.74049 * $y) - |
337
|
|
|
|
|
|
|
(0.06223 * _pow($y, 2)) - |
338
|
|
|
|
|
|
|
(0.00823 * _pow($y, 3)) + |
339
|
|
|
|
|
|
|
(0.00032 * _pow($y, 4)); |
340
|
|
|
|
|
|
|
} |
341
|
|
|
|
|
|
|
} |
342
|
|
|
|
|
|
|
|
343
|
8
|
|
|
|
|
17
|
return $jde0; |
344
|
|
|
|
|
|
|
} |
345
|
|
|
|
|
|
|
|
346
|
|
|
|
|
|
|
sub _pow { |
347
|
24
|
|
|
24
|
|
48
|
my ($n, $m) = @_; |
348
|
|
|
|
|
|
|
|
349
|
24
|
|
|
|
|
36
|
my $r = 1; |
350
|
24
|
|
|
|
|
46
|
foreach (1..$m) { |
351
|
72
|
|
|
|
|
111
|
$r *= $n; |
352
|
|
|
|
|
|
|
} |
353
|
|
|
|
|
|
|
|
354
|
24
|
|
|
|
|
62
|
return $r; |
355
|
|
|
|
|
|
|
} |
356
|
|
|
|
|
|
|
|
357
|
|
|
|
|
|
|
sub _cos { |
358
|
208
|
|
|
208
|
|
317
|
my ($degree) = @_; |
359
|
|
|
|
|
|
|
|
360
|
208
|
|
|
|
|
517
|
return cos(($degree * $PI)/180); |
361
|
|
|
|
|
|
|
} |
362
|
|
|
|
|
|
|
|
363
|
|
|
|
|
|
|
=head1 AUTHOR |
364
|
|
|
|
|
|
|
|
365
|
|
|
|
|
|
|
Mohammad S Anwar, C<< <mohammad.anwar at yahoo.com> >> |
366
|
|
|
|
|
|
|
|
367
|
|
|
|
|
|
|
=head1 REPOSITORY |
368
|
|
|
|
|
|
|
|
369
|
|
|
|
|
|
|
L<https://github.com/manwar/Astro-Utils> |
370
|
|
|
|
|
|
|
|
371
|
|
|
|
|
|
|
=head1 BUGS |
372
|
|
|
|
|
|
|
|
373
|
|
|
|
|
|
|
Please report any bugs or feature requests to C<bug-astro-utils at rt.cpan.org>, |
374
|
|
|
|
|
|
|
or through the web interface at L<http://rt.cpan.org/NoAuth/ReportBug.html?Queue=Astro-Utils>. |
375
|
|
|
|
|
|
|
I will be notified and then you'll automatically be notified of progress on your |
376
|
|
|
|
|
|
|
bug as I make changes. |
377
|
|
|
|
|
|
|
|
378
|
|
|
|
|
|
|
=head1 SUPPORT |
379
|
|
|
|
|
|
|
|
380
|
|
|
|
|
|
|
You can find documentation for this module with the perldoc command. |
381
|
|
|
|
|
|
|
|
382
|
|
|
|
|
|
|
perldoc Astro::Utils |
383
|
|
|
|
|
|
|
|
384
|
|
|
|
|
|
|
You can also look for information at: |
385
|
|
|
|
|
|
|
|
386
|
|
|
|
|
|
|
=over 4 |
387
|
|
|
|
|
|
|
|
388
|
|
|
|
|
|
|
=item * RT: CPAN's request tracker (report bugs here) |
389
|
|
|
|
|
|
|
|
390
|
|
|
|
|
|
|
L<http://rt.cpan.org/NoAuth/Bugs.html?Dist=Astro-Utils> |
391
|
|
|
|
|
|
|
|
392
|
|
|
|
|
|
|
=item * AnnoCPAN: Annotated CPAN documentation |
393
|
|
|
|
|
|
|
|
394
|
|
|
|
|
|
|
L<http://annocpan.org/dist/Astro-Utils> |
395
|
|
|
|
|
|
|
|
396
|
|
|
|
|
|
|
=item * CPAN Ratings |
397
|
|
|
|
|
|
|
|
398
|
|
|
|
|
|
|
L<http://cpanratings.perl.org/d/Astro-Utils> |
399
|
|
|
|
|
|
|
|
400
|
|
|
|
|
|
|
=item * Search CPAN |
401
|
|
|
|
|
|
|
|
402
|
|
|
|
|
|
|
L<http://search.cpan.org/dist/Astro-Utils/> |
403
|
|
|
|
|
|
|
|
404
|
|
|
|
|
|
|
=back |
405
|
|
|
|
|
|
|
|
406
|
|
|
|
|
|
|
=head1 LICENSE AND COPYRIGHT |
407
|
|
|
|
|
|
|
|
408
|
|
|
|
|
|
|
Copyright (C) 2015 - 2017 Mohammad S Anwar. |
409
|
|
|
|
|
|
|
|
410
|
|
|
|
|
|
|
This program is free software; you can redistribute it and / or modify it under |
411
|
|
|
|
|
|
|
the terms of the the Artistic License (2.0). You may obtain a copy of the full |
412
|
|
|
|
|
|
|
license at: |
413
|
|
|
|
|
|
|
|
414
|
|
|
|
|
|
|
L<http://www.perlfoundation.org/artistic_license_2_0> |
415
|
|
|
|
|
|
|
|
416
|
|
|
|
|
|
|
Any use, modification, and distribution of the Standard or Modified Versions is |
417
|
|
|
|
|
|
|
governed by this Artistic License.By using, modifying or distributing the Package, |
418
|
|
|
|
|
|
|
you accept this license. Do not use, modify, or distribute the Package, if you do |
419
|
|
|
|
|
|
|
not accept this license. |
420
|
|
|
|
|
|
|
|
421
|
|
|
|
|
|
|
If your Modified Version has been derived from a Modified Version made by someone |
422
|
|
|
|
|
|
|
other than you,you are nevertheless required to ensure that your Modified Version |
423
|
|
|
|
|
|
|
complies with the requirements of this license. |
424
|
|
|
|
|
|
|
|
425
|
|
|
|
|
|
|
This license does not grant you the right to use any trademark, service mark, |
426
|
|
|
|
|
|
|
tradename, or logo of the Copyright Holder. |
427
|
|
|
|
|
|
|
|
428
|
|
|
|
|
|
|
This license includes the non-exclusive, worldwide, free-of-charge patent license |
429
|
|
|
|
|
|
|
to make, have made, use, offer to sell, sell, import and otherwise transfer the |
430
|
|
|
|
|
|
|
Package with respect to any patent claims licensable by the Copyright Holder that |
431
|
|
|
|
|
|
|
are necessarily infringed by the Package. If you institute patent litigation |
432
|
|
|
|
|
|
|
(including a cross-claim or counterclaim) against any party alleging that the |
433
|
|
|
|
|
|
|
Package constitutes direct or contributory patent infringement,then this Artistic |
434
|
|
|
|
|
|
|
License to you shall terminate on the date that such litigation is filed. |
435
|
|
|
|
|
|
|
|
436
|
|
|
|
|
|
|
Disclaimer of Warranty: THE PACKAGE IS PROVIDED BY THE COPYRIGHT HOLDER AND |
437
|
|
|
|
|
|
|
CONTRIBUTORS "AS IS' AND WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES. THE IMPLIED |
438
|
|
|
|
|
|
|
WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, OR |
439
|
|
|
|
|
|
|
NON-INFRINGEMENT ARE DISCLAIMED TO THE EXTENT PERMITTED BY YOUR LOCAL LAW. UNLESS |
440
|
|
|
|
|
|
|
REQUIRED BY LAW, NO COPYRIGHT HOLDER OR CONTRIBUTOR WILL BE LIABLE FOR ANY DIRECT, |
441
|
|
|
|
|
|
|
INDIRECT, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING IN ANY WAY OUT OF THE USE |
442
|
|
|
|
|
|
|
OF THE PACKAGE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
443
|
|
|
|
|
|
|
|
444
|
|
|
|
|
|
|
=cut |
445
|
|
|
|
|
|
|
|
446
|
|
|
|
|
|
|
1; # End of Astro::Utils |