~ubuntu-branches/ubuntu/precise/rakudo/precise

« back to all changes in this revision

Viewing changes to src/setting/Num.pm

  • Committer: Bazaar Package Importer
  • Author(s): Alessandro Ghedini
  • Date: 2011-05-17 11:31:09 UTC
  • mfrom: (1.1.2 upstream)
  • Revision ID: james.westby@ubuntu.com-20110517113109-rmfir654u1axbpt4
Tags: 0.1~2011.04-1
* New upstream release (Closes: #601862, #585762, #577502)
* New maintainer
* Switch to 3.0 (quilt) format
* Update dependencies (Closes: #584498)
* Update debian/copyright to lastest DEP5 revision
* Do not generate/install perl6 manpage (now done by the build system)
* Enable tests
* Bump Standards-Version to 3.9.2 (no changes needed)
* Do not install extra LICENSE files and duplicated docs
* Remove debian/clean (no more needed)
* Add Vcs-* fields in debian/control
* Rewrite (short) description
* Update upstream copyright years
* Upload to unstable

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
class Num is also {
2
 
    multi method ACCEPTS($other) {
3
 
        if self eq 'NaN' {
4
 
            $other eq 'NaN';
5
 
        } else {
6
 
            $other == self;
7
 
        }
8
 
    }
9
 
    multi method ACCEPTS(Complex $other) {
10
 
        if self eq 'NaN' {
11
 
            $other.re eq 'NaN' || $other.im eq 'NaN';
12
 
        } else {
13
 
            $other.im == 0 && $other.re == self;
14
 
        }
15
 
    }
16
 
    multi method Complex() {
17
 
        Complex.new(self, 0);
18
 
    }
19
 
 
20
 
    our Num multi method exp() {
21
 
        my $r = Q:PIR {
22
 
            $N0 = self
23
 
            $N1 = exp $N0
24
 
            %r = box $N1
25
 
        };
26
 
    }
27
 
 
28
 
    our Num multi method acos($base = 'radians') {
29
 
        my $r = Q:PIR {
30
 
            $N0 = self
31
 
            $N1 = acos $N0
32
 
            %r = box $N1
33
 
        };
34
 
        $r!from-radians($base)
35
 
    }
36
 
 
37
 
    our Num multi method acosh($base = 'radians') {
38
 
        my $r = Q:PIR {
39
 
            $N0 = self
40
 
            $N1 = $N0 * $N0
41
 
            $N1 -= 1
42
 
            $N1 = sqrt $N1
43
 
            $N0 += $N1
44
 
            $N0 = ln $N0
45
 
            %r = box $N0
46
 
        };
47
 
        $r!from-radians($base)
48
 
    }
49
 
 
50
 
    our Num multi method acosec($base = 'radians') {
51
 
        my $r = Q:PIR {
52
 
            $N0 = self
53
 
            $N1 = 1 / $N0
54
 
            $N2 = asin $N1
55
 
            %r = box $N2
56
 
        };
57
 
        $r!from-radians($base)
58
 
   }
59
 
 
60
 
    our Num multi method acosech($base = 'radians') {
61
 
        # MUST: This is certainly wrong -- if nothing else,
62
 
        # asinh also calls from-radians on its result.
63
 
        # (Except it seems to be passing tests?)
64
 
        asinh(1/+self)!from-radians($base)
65
 
    }
66
 
 
67
 
    our Num multi method acotan($base = 'radians') {
68
 
        my $r = Q:PIR {
69
 
            $N0 = self
70
 
            $N1 = 1 / $N0
71
 
            $N2 = atan $N1
72
 
            %r = box $N2
73
 
        };
74
 
        $r!from-radians($base)
75
 
   }
76
 
 
77
 
    our Num multi method acotanh($base = 'radians') {
78
 
        my $r = Q:PIR {
79
 
            $N0 = self
80
 
            $N1 = 1 + $N0
81
 
            $N2 = $N0 - 1
82
 
            $N3 = $N1 / $N2
83
 
            $N4 = ln $N3
84
 
            $N4 = $N4 / 2
85
 
            %r = box $N4
86
 
        };
87
 
        $r!from-radians($base)
88
 
    }
89
 
 
90
 
    our Num multi method asec($base = 'radians') {
91
 
        my $r = Q:PIR {
92
 
            $N0 = self
93
 
            $N1 = asec $N0
94
 
            %r = box $N1
95
 
        };
96
 
        $r!from-radians($base)
97
 
   }
98
 
 
99
 
    our Num multi method asech($base = 'radians') {
100
 
        my $r = Q:PIR {
101
 
            $N0 = self
102
 
            $N1 = neg $N0
103
 
            $N1 *= $N0
104
 
            $N1 += 1
105
 
            $N1 = sqrt $N1
106
 
            $N1 += 1
107
 
            $N1 /= $N0
108
 
            $N1 = ln $N1
109
 
            %r = box $N1
110
 
        };
111
 
        $r!from-radians($base)
112
 
    }
113
 
 
114
 
    our Num multi method asin($base = 'radians') {
115
 
        my $r = Q:PIR {
116
 
            $N0 = self
117
 
            $N1 = asin $N0
118
 
            %r = box $N1
119
 
        };
120
 
        $r!from-radians($base)
121
 
    }
122
 
 
123
 
    our Num multi method asinh($base = 'radians') {
124
 
        my $r = Q:PIR {
125
 
            $N0 = self
126
 
            $N1 = $N0 * $N0
127
 
            $N1 += 1
128
 
            $N1 = sqrt $N1
129
 
            $N0 += $N1
130
 
            $N0 = ln $N0
131
 
            %r = box $N0
132
 
        };
133
 
        $r!from-radians($base)
134
 
    }
135
 
 
136
 
    our Num multi method atan($base = 'radians') {
137
 
        my $r = Q:PIR {
138
 
            $N0 = self
139
 
            $N1 = atan $N0
140
 
            %r = box $N1
141
 
        };
142
 
        $r!from-radians($base)
143
 
    }
144
 
 
145
 
    our Num multi method atan2(Num $x = 1, $base = 'radians') {
146
 
        my $r = Q:PIR {
147
 
            $N0 = self
148
 
            $P1 = find_lex "$x"
149
 
            $N1 = $P1
150
 
            $N2 = atan $N0, $N1
151
 
            %r = box $N2
152
 
        };
153
 
        $r!from-radians($base)
154
 
    }
155
 
 
156
 
    our Num multi method atanh($base = 'radians') {
157
 
        my $r = Q:PIR {
158
 
            $N0 = self
159
 
            $N1 = 1 - $N0
160
 
            $N0 += 1
161
 
            $N0 /= $N1
162
 
            $N0 = ln $N0
163
 
            $N0 /= 2
164
 
            %r = box $N0
165
 
        };
166
 
        $r!from-radians($base)
167
 
    }
168
 
 
169
 
    our Num multi method cos($base = 'radians') {
170
 
        my $x = self!to-radians($base);
171
 
        Q:PIR {
172
 
            $P0 = find_lex "$x"
173
 
            $N0 = $P0
174
 
            $N1 = cos $N0
175
 
            %r = box $N1
176
 
        };
177
 
    }
178
 
 
179
 
    our Num multi method cosh($base = 'radians') {
180
 
        my $x = self!to-radians($base);
181
 
        Q:PIR {
182
 
            $P0 = find_lex "$x"
183
 
            $N0 = $P0
184
 
            $N1 = cosh $N0
185
 
            %r = box $N1
186
 
        };
187
 
    }
188
 
 
189
 
    our Num multi method cosec($base = 'radians') {
190
 
        my $x = self!to-radians($base);
191
 
        Q:PIR {
192
 
            $P0 = find_lex "$x"
193
 
            $N0 = $P0
194
 
            $N1 = sin $N0
195
 
            $N1 = 1 / $N1
196
 
            %r = box $N1
197
 
        };
198
 
    }
199
 
 
200
 
    our Num multi method cosech($base = 'radians') {
201
 
        my $x = self!to-radians($base);
202
 
        Q:PIR {
203
 
            $P0 = find_lex "$x"
204
 
            $N0 = $P0
205
 
            $N1 = sinh $N0
206
 
            $N1 = 1 / $N1
207
 
            %r = box $N1
208
 
        };
209
 
   }
210
 
 
211
 
    our Num multi method cotan($base = 'radians') {
212
 
        my $x = self!to-radians($base);
213
 
        Q:PIR {
214
 
            $P0 = find_lex "$x"
215
 
            $N0 = $P0
216
 
            $N1 = tan $N0
217
 
            $N1 = 1 / $N1
218
 
            %r = box $N1
219
 
        }
220
 
    }
221
 
 
222
 
    our Num multi method cotanh($base = 'radians') {
223
 
        my $x = self!to-radians($base);
224
 
        Q:PIR {
225
 
            $P0 = find_lex "$x"
226
 
            $N0 = $P0
227
 
            $N1 = tanh $N0
228
 
            $N1 = 1 / $N1
229
 
            %r = box $N1
230
 
        }
231
 
   }
232
 
 
233
 
    multi method log() {
234
 
        Q:PIR {
235
 
            $N0 = self
236
 
            $N0 = ln $N0
237
 
            %r  = box $N0
238
 
        }
239
 
    }
240
 
 
241
 
    multi method log($base) {
242
 
        $.log / $base.log;
243
 
    }
244
 
 
245
 
    our method log10 {
246
 
        Q:PIR {
247
 
            $N0 = self
248
 
            $N0 = log10 $N0
249
 
            %r  = box $N0
250
 
        }
251
 
    }
252
 
 
253
 
    our Str multi method perl() {
254
 
        ~self
255
 
    }
256
 
 
257
 
    sub _modf($num) { my $q = $num.Int; $num - $q, $q; }
258
 
 
259
 
    multi method Rat($epsilon = 1.0e-6) {
260
 
        my $num = +self;
261
 
        my $signum = $num < 0 ?? -1 !! 1;
262
 
        $num = -$num if $signum == -1;
263
 
 
264
 
        # Find convergents of the continued fraction.
265
 
 
266
 
        my ($r, $q) = _modf($num);
267
 
        my ($a, $b) = 1, $q;
268
 
        my ($c, $d) = 0, 1;
269
 
 
270
 
        while $r != 0 && abs($num - ($b/$d)) > $epsilon {
271
 
            ($r, $q) = _modf(1/$r);
272
 
 
273
 
            ($a, $b) = ($b, $q*$b + $a);
274
 
            ($c, $d) = ($d, $q*$d + $c);
275
 
        }
276
 
 
277
 
        # Note that this result has less error than any Rational with a
278
 
        # smaller denominator but it is not (necessarily) the Rational
279
 
        # with the smallest denominator that has less than $epsilon error.
280
 
        # However, to find that Rational would take more processing.
281
 
 
282
 
        Rat.new($signum * $b, $d);
283
 
    }
284
 
 
285
 
    our Num multi method sec($base = 'radians') {
286
 
        my $x = self!to-radians($base);
287
 
        Q:PIR {
288
 
            $P0 = find_lex "$x"
289
 
            $N0 = $P0
290
 
            $N1 = sec $N0
291
 
            %r = box $N1
292
 
        }
293
 
    }
294
 
 
295
 
    our Num multi method sech($base = 'radians') {
296
 
        my $x = self!to-radians($base);
297
 
        Q:PIR {
298
 
            $P0 = find_lex "$x"
299
 
            $N0 = $P0
300
 
            $N1 = sech $N0
301
 
            %r = box $N1
302
 
        }
303
 
    }
304
 
 
305
 
    our Num multi method sin($base = 'radians') {
306
 
        my $x = self!to-radians($base);
307
 
        Q:PIR {
308
 
            $P0 = find_lex "$x"
309
 
            $N0 = $P0
310
 
            $N1 = sin $N0
311
 
            %r = box $N1
312
 
        }
313
 
    }
314
 
 
315
 
    our Num multi method sinh($base = 'radians') {
316
 
        my $x = self!to-radians($base);
317
 
        Q:PIR {
318
 
            $P0 = find_lex "$x"
319
 
            $N0 = $P0
320
 
            $N1 = sinh $N0
321
 
            %r = box $N1
322
 
        }
323
 
    }
324
 
 
325
 
    multi method sign {
326
 
        self ~~ NaN ?? NaN !! self <=> 0;
327
 
    }
328
 
 
329
 
    multi method sqrt() {
330
 
        Q:PIR {
331
 
            $N0 = self
332
 
            $N0 = sqrt $N0
333
 
            %r  = box $N0
334
 
        }
335
 
    }
336
 
 
337
 
    our Str multi method Str() {
338
 
        ~self
339
 
    }
340
 
 
341
 
    our Num multi method Num() {
342
 
        self;
343
 
    }
344
 
 
345
 
    our Num multi method tan($base = 'radians') {
346
 
        my $x = self!to-radians($base);
347
 
        Q:PIR {
348
 
            $P0 = find_lex "$x"
349
 
            $N0 = $P0
350
 
            $N1 = tan $N0
351
 
            %r = box $N1
352
 
        }
353
 
    }
354
 
 
355
 
    our Num multi method tanh($base = 'radians') {
356
 
        my $x = self!to-radians($base);
357
 
        Q:PIR {
358
 
            $P0 = find_lex "$x"
359
 
            $N0 = $P0
360
 
            $N1 = tanh $N0
361
 
            %r = box $N1
362
 
        }
363
 
    }
364
 
 
365
 
    our Complex multi method unpolar(Num $angle) is export {
366
 
        Complex.new(self * $angle.cos("radians"), self * $angle.sin("radians"));
367
 
    }
368
 
}
369
 
 
370
 
# vim: ft=perl6