File Coverage

blib/lib/Math/Decimal.pm
Criterion Covered Total %
statement 201 201 100.0
branch 154 154 100.0
condition 36 36 100.0
subroutine 32 32 100.0
pod 19 19 100.0
total 442 442 100.0


line stmt bran cond sub pod time code
1             =head1 NAME
2              
3             Math::Decimal - arithmetic in decimal
4              
5             =head1 SYNOPSIS
6              
7             use Math::Decimal qw($dec_number_rx);
8              
9             if($arg =~ /\A$dec_number_rx\z/o) { ...
10             # and other regular expressions
11              
12             use Math::Decimal qw(is_dec_number check_dec_number);
13              
14             if(is_dec_number($arg)) { ...
15             check_dec_number($arg);
16              
17             use Math::Decimal qw(dec_canonise);
18              
19             $r = dec_canonise($a);
20              
21             use Math::Decimal qw(
22             dec_sgn dec_abs
23             dec_cmp dec_min dec_max
24             dec_neg dec_add dec_sub
25             dec_pow10 dec_mul_pow10
26             dec_mul
27             dec_rndiv_and_rem dec_rndiv
28             dec_round_and_rem dec_round
29             dec_rem);
30              
31             $v = dec_sgn($a);
32             $v = dec_abs($a);
33             @v = sort { dec_cmp($a, $b) } @a;
34             $v = dec_min($a, $b);
35             $v = dec_max($a, $b);
36             $v = dec_neg($a);
37             $v = dec_add($a, $b);
38             $v = dec_sub($a, $b);
39             $v = dec_pow10($a);
40             $v = dec_mul_pow10($a, $b);
41             $v = dec_mul($a, $b);
42             ($q, $r) = dec_rndiv_and_rem("NEAR_EVN", $a, $b);
43             $q = dec_rndiv("NEAR_EVN", $a, $b);
44             ($v, $r) = dec_round_and_rem("NEAR_EVN", $a, $b);
45             $v = dec_round("NEAR_EVN", $a, $b);
46             $r = dec_rem("NEAR_EVN", $a, $b);
47              
48             =head1 DESCRIPTION
49              
50             This module performs basic arithmetic with arbitrary-precision numbers
51             expressed in decimal in ordinary Perl strings. The numbers can be
52             arbitrarily large, and can involve arbitrarily small fractions, and
53             all results are exact. This differs from Perl's standard arithmetic,
54             which is limited-precision binary (floating point) arithmetic. However,
55             because Perl performs implicit conversions between strings and numbers,
56             using decimal in the string form, it is extremely easy to exchange values
57             between this module and Perl's native arithmetic.
58              
59             Although Perl's scalars have space to store a number directly, that is
60             not used here. This module operates only on the string part of scalars,
61             ignoring the Perlish numerics entirely. It is not confused by dualvars
62             (scalars with independent string and number values).
63              
64             Numbers are represented in strings in a simple format, consisting of
65             optional sign, one or more integer digits, then optionally a dot (for
66             the decimal point) and one or more fractional digits. All representable
67             numbers have infinitely many acceptable representations (by adding leading
68             and trailing zero digits). The functions of this module consistently
69             return numbers in their shortest possible form.
70              
71             This module is intended for situations where exact numeric behaviour is
72             important, and Perl's default arithmetic is inadequate because fractions
73             or large numbers are involved, but the arithmetic makes up only a small
74             part of the program's behaviour. In those situations, it is convenient
75             that the functions here operate directly on strings that are useful
76             elsewhere in the program. If arithmetic is a large part of the program,
77             it will probably be better to use specialised (non-string) numeric object
78             types, such as those of L. These objects are less convenient
79             for interoperation, but arithmetic with them is more efficient.
80              
81             If you need to represent arbitrary (non-decimal) fractions exactly,
82             such as 1/3, then this module is not suitable. In that case you need a
83             general rational arithmetic module, such as L. Be prepared
84             to pay a large performance penalty for it.
85              
86             Most of this module is implemented in XS, with a pure Perl backup version
87             for systems that can't handle XS.
88              
89             =head1 THEORY
90              
91             The numbers processed by this module, the decimals, are those of the
92             form M * 10^-E, where M is an integer and E is a non-negative integer,
93             with range otherwise unlimited. (For any such number there are actually
94             an infinite number of possible (M, E) tuples: if a certain E value is
95             possible then all greater integers are also possible E values.) It is
96             an infinite set of cardinality aleph-0 (although this implementation is
97             hampered by the finiteness of computer memory). The set includes both
98             positive and negative numbers, and zero. It is a proper superset of the
99             integers, and a proper subset of the rationals. There are no infinite
100             numbers, nulls, irrationals, non-real complex numbers, or signed zeroes.
101              
102             Like the set of integers, the set of decimals is closed under mathematical
103             addition, subtraction, and multiplication. It thus forms a commutative
104             ring (in fact, an integral domain). Unlike the set of rationals, it is
105             not closed under exact division, and so it does not form a field.
106              
107             The arithmetic operations supplied by this module are those of ordinary
108             mathematical arithmetic. They thus obey the usual identities, such as
109             associativity (of addition and multiplication) and cancellation laws.
110             (This is unlike floating point arithmetic. Any system of floating
111             point numbers is not closed under mathematical addition, for example,
112             but by construction it is closed under floating point addition, which
113             necessarily differs from mathematical addition. Floating point addition
114             does not obey associativity or cancellation laws.)
115              
116             =head1 ROUNDING MODES
117              
118             For rounding division operations, a rounding mode must be specified.
119             It is given as a short string, which may be any of these:
120              
121             =over
122              
123             =item B
124              
125             towards zero
126              
127             =item B
128              
129             away from zero
130              
131             =item B
132              
133             floor: downwards (toward negative infinity)
134              
135             =item B
136              
137             ceiling: upwards (toward positive infinity)
138              
139             =item B
140              
141             to even
142              
143             =item B
144              
145             to odd
146              
147             =item BI
148              
149             to nearest, breaking ties according to I (which must be one of
150             the six above)
151              
152             =item B
153              
154             C if any rounding is required
155              
156             =back
157              
158             The mode "B" (rounding to nearest, breaking ties to the even
159             number), commonly known as "bankers' rounding", is usually the best for
160             general rounding purposes.
161              
162             =cut
163              
164             package Math::Decimal;
165              
166 18     18   1256125 { use 5.006; }
  18         177  
167 18     18   136 use warnings;
  18         54  
  18         729  
168 18     18   125 use strict;
  18         64  
  18         577  
169              
170 18     18   135 use Carp qw(croak);
  18         46  
  18         1281  
171 18     18   5913 use Params::Classify 0.000 qw(is_string);
  18         34759  
  18         1426  
172              
173             our $VERSION = "0.004";
174              
175 18     18   146 use parent "Exporter";
  18         43  
  18         85  
176             our @EXPORT_OK = qw(
177             $dec_number_rx $dec_integer_rx $dec_zero_rx $dec_one_rx $dec_negone_rx
178             is_dec_number check_dec_number
179             dec_canonise
180             dec_sgn dec_abs
181             dec_cmp dec_min dec_max
182             dec_neg dec_add dec_sub
183             dec_pow10 dec_mul_pow10
184             dec_mul
185             dec_rndiv_and_rem dec_rndiv dec_round_and_rem dec_round dec_rem
186             );
187              
188             eval { local $SIG{__DIE__};
189             require XSLoader;
190             XSLoader::load(__PACKAGE__, $VERSION);
191             };
192              
193             =head1 REGULAR EXPRESSIONS
194              
195             Each of these regular expressions matches some subset of numbers, in
196             the string form used by this module. The regular expressions do not
197             include any anchors, so to check whether an entire string matches a
198             number format you must supply the anchors yourself.
199              
200             =over
201              
202             =item $dec_number_rx
203              
204             Any number processed by this module. This checks the syntax in
205             which the number is expressed, without restricting its numeric value.
206             The number syntax consists of optional sign, one or more integer digits,
207             then optionally a dot (for the decimal point) and one or more fractional
208             digits. It is not permitted to have no integer digits, nor to have no
209             fractional digits if there is a decimal point. All digits must be ASCII
210             decimal digits. Unlike Perl's standard string-to-number conversions,
211             whitespace and other non-numeric parts are not permitted.
212              
213             =cut
214              
215             our $dec_number_rx = qr/[-+]?[0-9]+(?:\.[0-9]+)?/;
216              
217             =item $dec_integer_rx
218              
219             Any integer. This recognises integer values expressed in the
220             decimal format used by this module, I an integer-specific format.
221             So fractional decimal digits are allowed, provided that they are all zero,
222             as in "C<123.000>".
223              
224             =cut
225              
226             our $dec_integer_rx = qr/[-+]?[0-9]+(?:\.0+)?/;
227              
228             =item $dec_zero_rx
229              
230             Zero. This may have arbitrarily many integer and fractional digits,
231             and may be expressed with either sign.
232              
233             =cut
234              
235             our $dec_zero_rx = qr/[-+]?0+(?:\.0+)?/;
236              
237             =item $dec_one_rx
238              
239             Positive one.
240              
241             =cut
242              
243             our $dec_one_rx = qr/\+?0*1(?:\.0+)?/;
244              
245             =item $dec_negone_rx
246              
247             Negative one.
248              
249             =cut
250              
251             our $dec_negone_rx = qr/-0*1(?:\.0+)?/;
252              
253             =back
254              
255             =head1 FUNCTIONS
256              
257             Each C function takes one or more decimal arguments (I, I)
258             to operate on. If these arguments are not valid decimal numbers then
259             the function will C. Results are always returned as decimals in
260             minimum-length (canonical) form.
261              
262             =head2 Classification
263              
264             =over
265              
266             =item is_dec_number(ARG)
267              
268             Returns a truth value indicating whether I is a plain string
269             satisfying the decimal number syntax.
270              
271             =cut
272              
273 9   100 9 1 82 unless(defined &is_dec_number) { { local $SIG{__DIE__}; eval q{
  9     15404   24  
  9         775  
  15404         1191283  
274             sub is_dec_number($) {
275             no warnings "utf8";
276             return is_string($_[0]) && $_[0] =~ /\A$dec_number_rx\z/o;
277             }
278             }; } die $@ if $@ ne "" }
279              
280             =item check_dec_number(ARG)
281              
282             Checks whether I is a plain string satisfying the decimal number
283             syntax. Returns normally if it is. Cs if it is not.
284              
285             =cut
286              
287 15134 100   15134 1 291083 unless(defined &check_dec_number) { { local $SIG{__DIE__}; eval q{
288             sub check_dec_number($) {
289             croak "not a decimal number" unless &is_dec_number;
290             }
291             }; } die $@ if $@ ne "" }
292              
293             =back
294              
295             =head2 Representation
296              
297             =over
298              
299             =item dec_canonise(A)
300              
301             This returns the value I, numerically unmodified, but expressed
302             in minimum-length (canonical) form. Numerically this is the identity
303             function.
304              
305             =cut
306              
307 130298 100   130298 1 553302 unless(defined &dec_canonise) { { local $SIG{__DIE__}; eval q{
  130288 100       596243  
  130146 100       543579  
  130146 100       1405325  
    100          
308             sub dec_canonise($) {
309             croak "not a decimal number" unless is_string($_[0]);
310             $_[0] =~ /\A(?:(-)|\+?)0*([1-9][0-9]*|0)(?:(\.[0-9]*[1-9])0*|\.0+|)\z/
311             or croak "not a decimal number";
312             my $num = (defined($1) ? $1 : "").$2.(defined($3) ? $3 : "");
313             return $num eq "-0" ? "0" : $num;
314             }
315             }; } die $@ if $@ ne "" }
316              
317             =back
318              
319             =head2 Arithmetic
320              
321             =over
322              
323             =item dec_sgn(A)
324              
325             Returns +1 if the argument is positive, 0 if the argument is zero,
326             or -1 if the argument is negative.
327              
328             The value returned is not just a string, as usual for this module, but
329             has also been subjected to Perl's implicit numerification. This is
330             necessary for it to be an acceptable comparison value in a C
331             operation, on Perls prior to 5.11.0, due to perl bug #69384.
332              
333             =cut
334              
335             my @sgn_result = ("-1", "0", "1");
336             foreach(@sgn_result) {
337 18     18   8544 no warnings "void";
  18         47  
  18         15829  
338             $_ + 0;
339             }
340              
341 5981 100   5981 1 190202 unless(defined &dec_sgn) { { local $SIG{__DIE__}; eval q{
  5871 100       111617  
  5090 100       105012  
    100          
342             sub dec_sgn($) {
343             croak "not a decimal number" unless is_string($_[0]);
344             $_[0] =~ /\A(?:(-)|\+?)0*(?:0(?:\.0+)?()|[0-9]+(?:\.[0-9]+)?)\z/
345             or croak "not a decimal number";
346             return $sgn_result[defined($2) ? 1 : defined($1) ? 0 : 2];
347             }
348             }; } die $@ if $@ ne "" }
349              
350             =item dec_abs(A)
351              
352             Absolute value (magnitude, discarding sign).
353              
354             =cut
355              
356 4761 100   4761 1 62587 unless(defined &dec_abs) { { local $SIG{__DIE__}; eval q{
  4751         9008  
  4751         12972  
  4751         97164  
357             sub dec_abs($) {
358             croak "not a decimal number" unless is_string($_[0]);
359             my $a = $_[0];
360             $a =~ s/\A-(?=[0-9])//;
361             return dec_canonise($a);
362             }
363             }; } die $@ if $@ ne "" }
364              
365             =item dec_cmp(A, B)
366              
367             Arithmetic comparison. Returns -1, 0, or +1, indicating whether I is
368             less than, equal to, or greater than I.
369              
370             The value returned is not just a string, as usual for this module, but
371             has also been subjected to Perl's implicit numerification. This is
372             necessary for it to be an acceptable comparison value in a C
373             operation, on Perls prior to 5.11.0, due to perl bug #69384.
374              
375             =cut
376              
377 9 100 100 9 1 62 unless(defined &dec_cmp) { { local $SIG{__DIE__}; eval q{
  9 100 100 81393   19  
  9 100 100     3714  
  81393 100 100     11859810  
  81333 100       451240  
  81333 100       365678  
  81333 100       338502  
  80907 100       166261  
  80907 100       151224  
  80907 100       148467  
  80907 100       148286  
  80907 100       255690  
  80907 100       260706  
  80907 100       197148  
  80907         1176059  
  40267         70472  
  40267         101597  
  7771         20080  
  18840         44357  
  40267         70350  
  40267         90715  
  9642         20683  
  8452         17543  
  40267         90680  
  40267         1018773  
378             my %sgn_cmp = (
379             "+0" => "1",
380             "+-" => "1",
381             "0+" => "-1",
382             "00" => "0",
383             "0-" => "1",
384             "-+" => "-1",
385             "-0" => "-1",
386             );
387             foreach(values %sgn_cmp) {
388             no warnings "void";
389             $_ + 0;
390             }
391              
392             sub dec_cmp($$) {
393             croak "not a decimal number"
394             unless is_string($_[0]) && is_string($_[1]);
395             my($as, $ai, $af) = ($_[0] =~ /\A([-+])?([0-9]+)(?:\.([0-9]+))?\z/);
396             my($bs, $bi, $bf) = ($_[1] =~ /\A([-+])?([0-9]+)(?:\.([0-9]+))?\z/);
397             croak "not a decimal number" unless defined($ai) && defined($bi);
398             $as = "+" unless defined $as;
399             $bs = "+" unless defined $bs;
400             $af = "0" unless defined $af;
401             $bf = "0" unless defined $bf;
402             $as = "0" if $ai =~ /\A0+\z/ && $af =~ /\A0+\z/;
403             $bs = "0" if $bi =~ /\A0+\z/ && $bf =~ /\A0+\z/;
404             my $cmp = $sgn_cmp{$as.$bs};
405             return $cmp if defined $cmp;
406             my $ld = length($ai) - length($bi);
407             if($ld < 0) {
408             $ai = ("0" x -$ld) . $ai;
409             } elsif($ld > 0) {
410             $bi = ("0" x $ld) . $bi;
411             }
412             $ld = length($af) - length($bf);
413             if($ld < 0) {
414             $af .= "0" x -$ld;
415             } elsif($ld > 0) {
416             $bf .= "0" x $ld;
417             }
418             ($ai, $af, $bi, $bf) = ($bi, $bf, $ai, $af) if $as eq "-";
419             return $sgn_result[($ai.$af cmp $bi.$bf) + 1];
420             }
421             }; } die $@ if $@ ne "" }
422              
423             =item dec_min(A, B)
424              
425             Arithmetic minimum. Returns the arithmetically lesser of the two arguments.
426              
427             =cut
428              
429 20898 100   20898 1 508968 unless(defined &dec_min) { { local $SIG{__DIE__}; eval q{
430             sub dec_min($$) { dec_canonise($_[&dec_cmp eq "-1" ? 0 : 1]) }
431             }; } die $@ if $@ ne "" }
432              
433             =item dec_max(A, B)
434              
435             Arithmetic maximum. Returns the arithmetically greater of the two arguments.
436              
437             =cut
438              
439 20898 100   20898 1 11817442 unless(defined &dec_max) { { local $SIG{__DIE__}; eval q{
440             sub dec_max($$) { dec_canonise($_[&dec_cmp eq "1" ? 0 : 1]) }
441             }; } die $@ if $@ ne "" }
442              
443             =item dec_neg(A)
444              
445             Negation: returns -A.
446              
447             =cut
448              
449 14864     14864 1 84697 unless(defined &dec_neg) { { local $SIG{__DIE__}; eval q{
  14864         299269  
  14702         73091  
  14702         57318  
  14702         300281  
450             my %negate_sign = (
451             "" => "-",
452             "+" => "-",
453             "-" => "+",
454             );
455              
456             sub dec_neg($) {
457             my $a = $_[0];
458             check_dec_number($a);
459             $a =~ s/\A([-+]?)/$negate_sign{$1}/e;
460             return dec_canonise($a);
461             }
462             }; } die $@ if $@ ne "" }
463              
464             =item dec_add(A, B)
465              
466             Addition: returns A + B.
467              
468             =cut
469              
470 23400 100 100 23400 1 2551203 unless(defined &dec_add) { { local $SIG{__DIE__}; eval q{
  23370 100 100     136590  
  23370 100       112711  
  23370 100       112109  
  23157 100       55994  
  23157 100       48349  
  23157 100       44498  
  23157 100       45862  
  23157 100       35857  
  23157 100       43708  
  23157 100       61834  
  3022 100       9375  
  9835 100       27384  
  23157 100       43364  
  23157 100       58158  
  2538 100       6227  
  6343 100       14373  
  23157         42387  
  23157         44561  
  23157         39944  
  23157         47893  
  10843         16753  
  10843         21510  
  10843         27170  
  48433         103370  
  48433         88503  
  48433         90866  
  48433         119910  
  10843         281202  
  12314         33798  
  12314         20591  
  12314         27532  
  12314         30056  
  53839         110664  
  53839         106367  
  53839         101329  
  53839         130809  
  12314         311509  
471             sub dec_add($$) {
472             croak "not a decimal number"
473             unless is_string($_[0]) && is_string($_[1]);
474             my($as, $ai, $af) = ($_[0] =~ /\A([-+])?([0-9]+)(?:\.([0-9]+))?\z/);
475             my($bs, $bi, $bf) = ($_[1] =~ /\A([-+])?([0-9]+)(?:\.([0-9]+))?\z/);
476             croak "not a decimal number" unless defined($ai) && defined($bi);
477             $as = "+" unless defined $as;
478             $bs = "+" unless defined $bs;
479             $af = "0" unless defined $af;
480             $bf = "0" unless defined $bf;
481             {
482             my $ld = length($ai) - length($bi);
483             if($ld < 0) {
484             $ai = ("0" x -$ld) . $ai;
485             } elsif($ld > 0) {
486             $bi = ("0" x $ld) . $bi;
487             }
488             $ld = length($af) - length($bf);
489             if($ld < 0) {
490             $af .= "0" x -$ld;
491             } elsif($ld > 0) {
492             $bf .= "0" x $ld;
493             }
494             }
495             my $il = length($ai);
496             my $ad = $ai.$af;
497             my $bd = $bi.$bf;
498             if($as eq $bs) {
499             # same sign, add magnitudes
500             my $c = 0;
501             my $rd = " " x length($ad);
502             for(my $pos = length($ad); $pos--; ) {
503             my $rv = ord(substr($ad, $pos, 1)) +
504             (ord(substr($bd, $pos, 1)) - 0x30) + $c;
505             $c = $rv >= 0x3a ? 1 : 0;
506             $rv -= 10 if $c;
507             substr $rd, $pos, 1, chr($rv);
508             }
509             return dec_canonise($as.($c ? "1" : "").substr($rd, 0, $il).
510             ".".substr($rd, $il));
511             } else {
512             # different sign, subtract magnitudes
513             ($as, $ad, $bd) = ($bs, $bd, $ad) if $ad lt $bd;
514             my $c = 0;
515             my $rd = " " x length($ad);
516             for(my $pos = length($ad); $pos--; ) {
517             my $rv = ord(substr($ad, $pos, 1)) -
518             (ord(substr($bd, $pos, 1)) - 0x30) - $c;
519             $c = $rv < 0x30 ? 1 : 0;
520             $rv += 10 if $c;
521             substr $rd, $pos, 1, chr($rv);
522             }
523             return dec_canonise($as.substr($rd, 0, $il).
524             ".".substr($rd, $il));
525             }
526             }
527             }; } die $@ if $@ ne "" }
528              
529             =item dec_sub(A, B)
530              
531             Subtraction: returns A - B.
532              
533             =cut
534              
535 12367     12367 1 5386136 unless(defined &dec_sub) { { local $SIG{__DIE__}; eval q{
536             sub dec_sub($$) { dec_add($_[0], dec_neg($_[1])) }
537             }; } die $@ if $@ ne "" }
538              
539             =item dec_pow10(A)
540              
541             Power of ten: returns 10^A.
542             I must be an integer value (though it has the usual decimal syntax).
543             Cs if I is too large for Perl to handle the result.
544              
545             =cut
546              
547             unless(defined(&dec_pow10) && defined(&dec_mul_pow10)) {
548 20264 100 100 20264   57758 { local $SIG{__DIE__}; eval q{
  20244 100       94002  
  20244 100       61219  
  20102 100       39370  
  20092 100       41042  
  20088         387779  
549             sub _parse_expt($) {
550             croak "not a decimal number" unless is_string($_[0]);
551             my($pneg, $pi, $pbadf) =
552             ($_[0] =~ /\A(?:(-)|\+?)
553             0*(0|[1-9][0-9]*)
554             (?:|\.0+|\.[0-9]+())\z/x);
555             croak "not a decimal number" unless defined $pi;
556             croak "not an integer" if defined $pbadf;
557             croak "exponent too large" if length($pi) > 9;
558             return defined($pneg) && $pi ne "0" ? 0-$pi : 0+$pi;
559             }
560             }; } die $@ if $@ ne "" }
561              
562 198 100   198 1 102211 unless(defined &dec_pow10) { { local $SIG{__DIE__}; eval q{
  110         254  
  28         108  
  82         306  
563             sub dec_pow10($) {
564             my $p = &_parse_expt;
565             if($p < 0) {
566             return "0.".("0" x (-1-$p))."1";
567             } else {
568             return "1".("0" x $p);
569             }
570             }
571             }; } die $@ if $@ ne "" }
572              
573             =item dec_mul_pow10(A, B)
574              
575             Digit shifting: returns A * 10^B.
576             I must be an integer value (though it has the usual decimal syntax).
577             Cs if I is too large for Perl to handle the result.
578              
579             =cut
580              
581 20147 100   20147 1 7574152 unless(defined &dec_mul_pow10) { { local $SIG{__DIE__}; eval q{
  20137 100       103854  
  20137 100       55010  
  20066 100       38580  
  20066 100       360824  
  19978 100       52209  
  4293         6564  
  4293         12128  
  4293         82981  
  15685         26894  
  15685         41408  
  15685         304762  
582             sub dec_mul_pow10($$) {
583             croak "not a decimal number" unless is_string($_[0]);
584             my($as, $ai, $af) = ($_[0] =~ /\A([-+]?)([0-9]+)(?:\.([0-9]+))?\z/);
585             croak "not a decimal number" unless defined $ai;
586             $af = "" unless defined $af;
587             my $p = _parse_expt($_[1]);
588             if($p < 0) {
589             my $il = length($ai);
590             $ai = ("0" x (1-$p-$il)).$ai if $il+$p <= 0;
591             return dec_canonise($as.substr($ai, 0, $p).".".
592             substr($ai, $p).$af);
593             } else {
594             my $fl = length($af);
595             $af .= "0" x (1+$p-$fl) if $p >= $fl;
596             return dec_canonise($as.$ai.substr($af, 0, $p).".".
597             substr($af, $p));
598             }
599             }
600             }; } die $@ if $@ ne "" }
601              
602             =item dec_mul(A, B)
603              
604             Multiplication: returns A * B.
605              
606             =cut
607              
608 9 100 100 9 1 4679 unless(defined &dec_mul) { { local $SIG{__DIE__}; eval q{
  9 100 100 9   372  
  9 100   26175   55  
  9 100       739  
  9 100       24  
  9 100       38  
  26175 100       2169941  
  26155 100       138357  
  26155         113273  
  26155         111631  
  26013         56303  
  26013         50479  
  26013         51623  
  26013         49643  
  26013         44916  
  26013         46916  
  26013         41335  
  26013         37606  
  26013         36242  
  26013         52028  
  26013         59116  
  58669         106539  
  58669         128634  
  28723         40787  
  28723         56691  
  58136         86215  
  58136         93118  
  58136         99954  
  58136         84285  
  58136         115257  
  58136         78433  
  58136         128279  
  28723         76935  
  26013         630794  
609             sub dec_mul($$) {
610             croak "not a decimal number"
611             unless is_string($_[0]) && is_string($_[1]);
612             my($as, $ai, $af) =
613             ($_[0] =~ /\A([-+])?0*(0|[1-9][0-9]*)(?:\.([0-9]+))?\z/);
614             my($bs, $bi, $bf) =
615             ($_[1] =~ /\A([-+])?0*(0|[1-9][0-9]*)(?:\.([0-9]+))?\z/);
616             croak "not a decimal number" unless defined($ai) && defined($bi);
617             $as = "+" unless defined $as;
618             $bs = "+" unless defined $bs;
619             $af = "" unless defined $af;
620             $bf = "0" unless defined $bf;
621             my $il = length($ai) + length($bi);
622             my $ad = $ai.$af;
623             my $bd = $bi.$bf;
624             my $al = length($ad);
625             my $bl = length($bd);
626             my $rd = "0" x ($al+$bl);
627             for(my $bp = $bl; $bp--; ) {
628             my $bv = ord(substr($bd, $bp, 1)) - 0x30;
629             next if $bv == 0;
630             my $c = 0;
631             for(my $ap = $al; $ap--; ) {
632             my $rp = $ap + $bp + 1;
633             my $av = ord(substr($ad, $ap, 1)) - 0x30;
634             my $v = $av*$bv + $c + ord(substr($rd, $rp, 1)) - 0x30;
635             substr $rd, $rp, 1,
636             chr(do { use integer; $v%10 + 0x30 });
637             $c = do { use integer; $v / 10 };
638             }
639             substr $rd, $bp, 1, chr(ord(substr($rd, $bp, 1)) + $c);
640             }
641             return dec_canonise(($as eq $bs ? "+" : "-").substr($rd, 0, $il).
642             ".".substr($rd, $il));
643             }
644             }; } die $@ if $@ ne "" }
645              
646             =item dec_rndiv_and_rem(MODE, A, B)
647              
648             Rounding division: returns a list of two items, the quotient (I) and
649             remainder (I) from the division of I by I.
650             The quotient is by definition
651             integral, and the quantities are related by the equation Q*B + R = A.
652             I controls the rounding mode, which determines which integer I is
653             when I is non-zero.
654              
655             =cut
656              
657 4464 100 100 4464 1 14456 unless(defined &dec_rndiv_and_rem) { { local $SIG{__DIE__}; eval q{
  4434 100 100 6244   9531  
  4424 100       13640  
  4424 100       14445  
  4424 100       10751  
  4424 100       10537  
  4424 100       7482  
  4424 100       7164  
  4424 100       11584  
  4912 100       57768  
  4912 100       10552  
  35940 100       393773  
  35940 100       391180  
  4912         56034  
  4912         56047  
  4912         19886  
  4424         14406  
  6244         1418033  
  6244         48432  
  6084         74956  
  5274         59536  
  4464         51127  
  4464         47698  
  4464         12464  
  4434         15587  
  4434         7677  
  4434         36827  
  1440         17173  
  1440         16687  
  4432         93343  
658              
659             sub _nonneg_rndiv_and_rem_twz($$) {
660             croak "division by zero" if $_[1] eq "0";
661             return ("0", "0") if $_[0] eq "0";
662             $_[0] =~ /\A(?:[1-9]([0-9]*)|0\.(0*)[1-9])/;
663             my $a_expt = defined($1) ? length($1) : -1-length($2);
664             $_[1] =~ /\A(?:[1-9]([0-9]*)|0\.(0*)[1-9])/;
665             my $b_expt = defined($1) ? length($1) : -1-length($2);
666             my $q = "0";
667             my $r = $_[0];
668             for(my $s = $a_expt-$b_expt; $s >= 0; $s--) {
669             my $sd = dec_mul_pow10($_[1], $s);
670             for(my $m = 9; ; $m--) {
671             my $msd = dec_mul($sd, $m);
672             if(dec_cmp($msd, $r) ne "1") {
673             $q = dec_add($q, dec_mul_pow10($m, $s));
674             $r = dec_sub($r, $msd);
675             last;
676             }
677             }
678             }
679             return ($q, $r);
680             }
681              
682             my %round_tiebreak = (
683             (map { ($_ => $_, "NEAR_$_" => $_) } qw(TWZ AWZ FLR CLG EVN ODD)),
684             EXACT => "EXACT",
685             );
686              
687             my %round_positive = (
688             (map { my($f, $t) = split(/:/, $_); ($f => $t, "NEAR_$f" => "NEAR_$t") }
689             qw(TWZ:TWZ AWZ:AWZ FLR:TWZ CLG:AWZ EVN:EVN ODD:ODD)),
690             EXACT => "EXACT",
691             );
692              
693             my %round_negative = (
694             (map { my($f, $t) = split(/:/, $_); ($f => $t, "NEAR_$f" => "NEAR_$t") }
695             qw(TWZ:TWZ AWZ:AWZ FLR:AWZ CLG:TWZ EVN:EVN ODD:ODD)),
696             EXACT => "EXACT",
697             );
698              
699             my %base_round_handler = (
700             TWZ => sub { 0 },
701             AWZ => sub { 1 },
702             EVN => sub { $_[0] =~ /[13579]\z/ },
703             ODD => sub { $_[0] =~ /[02468]\z/ },
704             );
705              
706             sub dec_rndiv_and_rem($$$) {
707             my $mode = $_[0];
708             croak "invalid rounding mode"
709             unless is_string($mode) && exists($round_tiebreak{$mode});
710             my $sgn_a = dec_sgn($_[1]);
711             my $sgn_b = dec_sgn($_[2]);
712             my $abs_a = dec_abs($_[1]);
713             my $abs_b = dec_abs($_[2]);
714             my($q, $r) = _nonneg_rndiv_and_rem_twz($abs_a, $abs_b);
715             $mode = ($sgn_a == $sgn_b ? \%round_positive : \%round_negative)
716             ->{$mode};
717             my $half_cmp;
718             if(
719             $r eq "0" ? 0 :
720             $mode eq "EXACT" ? croak("inexact division") :
721             $mode =~ /\ANEAR_/ &&
722             ($half_cmp = dec_cmp(dec_mul($r, "2"), $abs_b))
723             ne "0" ?
724             $half_cmp eq "1" :
725             $base_round_handler{$round_tiebreak{$mode}}->($q)
726             ) {
727             $q = dec_add($q, "1");
728             $r = dec_sub($r, $abs_b);
729             }
730             return (($sgn_a ne $sgn_b ? dec_neg($q) : $q),
731             ($sgn_a ne "1" ? dec_neg($r) : $r));
732             }
733              
734             }; } die $@ if $@ ne "" }
735              
736             =item dec_rndiv(MODE, A, B)
737              
738             Rounding division: returns the quotient (I)
739             from the division of I by I.
740             The quotient is by definition integral, and approximates A/B. I
741             controls the rounding mode, which determines which integer I is when it
742             can't be exactly A/B.
743              
744             =cut
745              
746 1252     1252 1 227972 unless(defined &dec_rndiv) { { local $SIG{__DIE__}; eval q{
  888         5956  
747             sub dec_rndiv($$$) {
748             my($quotient, undef) = &dec_rndiv_and_rem;
749             return $quotient;
750             }
751             }; } die $@ if $@ ne "" }
752              
753             =item dec_round_and_rem(MODE, A, B)
754              
755             Rounding: returns a list of two items, the rounded value (I) and remainder
756             (I) from the rounding of I to a multiple of I. The rounded value is
757             an exact multiple of I, and the quantities are related by the equation
758             V + R = A. I controls the rounding mode, which determines which
759             multiple of I I is when I is non-zero.
760              
761             =cut
762              
763 1248     1248 1 229053 unless(defined &dec_round_and_rem) { { local $SIG{__DIE__}; eval q{
  886         12496  
764             sub dec_round_and_rem($$$) {
765             my($quotient, $remainder) = &dec_rndiv_and_rem;
766             return (dec_mul($_[2], $quotient), $remainder);
767             }
768             }; } die $@ if $@ ne "" }
769              
770             =item dec_round(MODE, A, B)
771              
772             Rounding: returns the rounded value (I) from the rounding of I to
773             a multiple of I. The rounded value is an exact multiple of I, and
774             approximates I. I controls the rounding mode, which determines
775             which multiple of I I is when it can't be exactly I.
776              
777             =cut
778              
779 1248     1248 1 522846 unless(defined &dec_round) { { local $SIG{__DIE__}; eval q{
  886         12498  
780             sub dec_round($$$) {
781             my($quotient, undef) = &dec_rndiv_and_rem;
782             return dec_mul($_[2], $quotient);
783             }
784             }; } die $@ if $@ ne "" }
785              
786             =item dec_rem(MODE, A, B)
787              
788             Remainder: returns the remainder (I) from the division of I by I.
789             I differs from I by an exact multiple of I.
790             I controls the rounding
791             mode, which determines which quotient is used when I is non-zero.
792              
793             =cut
794              
795 1248     1248 1 226127 unless(defined &dec_rem) { { local $SIG{__DIE__}; eval q{
  886         5422  
796             sub dec_rem($$$) {
797             my(undef, $remainder) = &dec_rndiv_and_rem;
798             return $remainder;
799             }
800             }; } die $@ if $@ ne "" }
801              
802             =back
803              
804             =head1 BUGS
805              
806             The implementation of division is hideously inefficient.
807             This should be improved in a future version.
808              
809             =head1 SEE ALSO
810              
811             L
812              
813             =head1 AUTHOR
814              
815             Andrew Main (Zefram)
816              
817             =head1 COPYRIGHT
818              
819             Copyright (C) 2009, 2010, 2011, 2017
820             Andrew Main (Zefram)
821              
822             =head1 LICENSE
823              
824             This module is free software; you can redistribute it and/or modify it
825             under the same terms as Perl itself.
826              
827             =cut
828              
829             1;