8 @EXPORT = qw( inf NaN );
12 ##############################################################################
14 # These are all alike, and thus faked by AUTOLOAD
16 my @faked = qw/round_mode accuracy precision div_scale/;
17 use vars qw/$VERSION $AUTOLOAD $_lite/; # _lite for testsuite
23 $name =~ s/.*:://; # split package
25 foreach my $n (@faked)
29 *{"bigrat::$name"} = sub
35 Math::BigInt->$name($_[0]);
36 Math::BigFloat->$name($_[0]);
37 return Math::BigRat->$name($_[0]);
39 return Math::BigInt->$name();
45 # delayed load of Carp and avoid recursion
47 Carp::croak ("Can't call bigrat\-\>$name, not a valid method");
56 # $Math::BigInt::upgrade = $_[0];
57 # $Math::BigFloat::upgrade = $_[0];
59 return $Math::BigInt::upgrade;
66 # see also bignum->import() for additional comments
69 my $lib = 'Calc'; my $upgrade = 'Math::BigFloat';
71 my @import = ( ':constant' ); # drive it w/ constant
72 my @a = @_; my $l = scalar @_; my $j = 0;
74 my ($ver,$trace); # version? trace?
75 for ( my $i = 0; $i < $l ; $i++,$j++ )
77 if ($_[$i] eq 'upgrade')
79 # this causes upgrading
80 $upgrade = $_[$i+1]; # or undef to disable
81 my $s = 2; $s = 1 if @a-$j < 2; # avoid "can not modify non-existant..."
82 splice @a, $j, $s; $j -= $s;
84 elsif ($_[$i] =~ /^(l|lib)$/)
86 # this causes a different low lib to take care...
87 $lib = $_[$i+1] || '';
88 my $s = 2; $s = 1 if @a-$j < 2; # avoid "can not modify non-existant..."
89 splice @a, $j, $s; $j -= $s;
91 elsif ($_[$i] =~ /^(v|version)$/)
94 splice @a, $j, 1; $j --;
96 elsif ($_[$i] =~ /^(t|trace)$/)
99 splice @a, $j, 1; $j --;
103 die ("unknown option $_[$i]");
107 $_lite = 0; # using M::BI::L ?
110 require Math::BigInt::Trace; $class = 'Math::BigInt::Trace';
111 $upgrade = 'Math::BigFloat::Trace';
115 # see if we can find Math::BigInt::Lite
116 if (!defined $a && !defined $p) # rounding won't work to well
118 eval 'require Math::BigInt::Lite;';
121 @import = ( ); # :constant in Lite, not MBI
122 Math::BigInt::Lite->import( ':constant' );
123 $_lite= 1; # signal okay
126 require Math::BigInt if $_lite == 0; # not already loaded?
127 $class = 'Math::BigInt'; # regardless of MBIL or not
129 # Math::BigInt::Trace or plain Math::BigInt
130 $class->import(@import, upgrade => $upgrade, lib => $lib);
132 require Math::BigFloat;
133 Math::BigFloat->import( upgrade => 'Math::BigRat', ':constant' );
134 require Math::BigRat;
137 print "bigrat\t\t\t v$VERSION\n";
138 print "Math::BigInt::Lite\t v$Math::BigInt::Lite::VERSION\n" if $_lite;
139 print "Math::BigInt\t\t v$Math::BigInt::VERSION";
140 my $config = Math::BigInt->config();
141 print " lib => $config->{lib} v$config->{lib_version}\n";
142 print "Math::BigFloat\t\t v$Math::BigFloat::VERSION\n";
143 print "Math::BigRat\t\t v$Math::BigRat::VERSION\n";
146 $self->export_to_level(1,$self,@a); # export inf and NaN
149 sub inf () { Math::BigInt->binf(); }
150 sub NaN () { Math::BigInt->bnan(); }
158 bigrat - Transparent BigNumber/BigRationale support for Perl
164 $x = 2 + 4.5,"\n"; # BigFloat 6.5
165 print 1/3 + 1/4,"\n"; # produces 7/12
169 All operators (inlcuding basic math operations) are overloaded. Integer and
170 floating-point constants are created as proper BigInts or BigFloats,
173 Other than L<bignum>, this module upgrades to Math::BigRat, meaning that
174 instead of 2.5 you will get 2+1/2 as output.
178 C<bigrat> is just a thin wrapper around various modules of the Math::BigInt
179 family. Think of it as the head of the family, who runs the shop, and orders
180 the others to do the work.
182 The following modules are currently used by bignum:
184 Math::BigInt::Lite (for speed, and only if it is loadable)
191 Math with the numbers is done (by default) by a module called
192 Math::BigInt::Calc. This is equivalent to saying:
194 use bigrat lib => 'Calc';
196 You can change this by using:
198 use bigrat lib => 'BitVect';
200 The following would first try to find Math::BigInt::Foo, then
201 Math::BigInt::Bar, and when this also fails, revert to Math::BigInt::Calc:
203 use bigrat lib => 'Foo,Math::BigInt::Bar';
205 Please see respective module documentation for further details.
209 The sign is either '+', '-', 'NaN', '+inf' or '-inf' and stored seperately.
211 A sign of 'NaN' is used to represent the result when input arguments are not
212 numbers or as a result of 0/0. '+inf' and '-inf' represent plus respectively
213 minus infinity. You will get '+inf' when dividing a positive number by 0, and
214 '-inf' when dividing any negative number by 0.
218 Since all numbers are not objects, you can use all functions that are part of
219 the BigInt or BigFloat API. It is wise to use only the bxxx() notation, and not
220 the fxxx() notation, though. This makes you independed on the fact that the
221 underlying object might morph into a different class than BigFloat.
225 But a warning is in order. When using the following to make a copy of a number,
226 only a shallow copy will be made.
231 Using the copy or the original with overloaded math is okay, e.g. the
235 print $x + 1, " ", $y,"\n"; # prints 10 9
237 but calling any method that modifies the number directly will result in
238 B<both> the original and the copy beeing destroyed:
241 print $x->badd(1), " ", $y,"\n"; # prints 10 10
244 print $x->binc(1), " ", $y,"\n"; # prints 10 10
247 print $x->bmul(2), " ", $y,"\n"; # prints 18 18
249 Using methods that do not modify, but testthe contents works:
252 $z = 9 if $x->is_zero(); # works fine
254 See the documentation about the copy constructor and C<=> in overload, as
255 well as the documentation in BigInt for further details.
259 perl -Mbigrat -le 'print sqrt(33)'
260 perl -Mbigrat -le 'print 2*255'
261 perl -Mbigrat -le 'print 4.5+2*255'
262 perl -Mbigrat -le 'print 3/7 + 5/7 + 8/3'
263 perl -Mbigrat -le 'print 12->is_odd()';
267 This program is free software; you may redistribute it and/or modify it under
268 the same terms as Perl itself.
272 Especially L<bignum>.
274 L<Math::BigFloat>, L<Math::BigInt>, L<Math::BigRat> and L<Math::Big> as well
275 as L<Math::BigInt::BitVect>, L<Math::BigInt::Pari> and L<Math::BigInt::GMP>.
279 (C) by Tels L<http://bloodgate.com/> in early 2002.