not_japh has asked for the wisdom of the Perl Monks concerning the following question:

Hey, all. What'd I goof up here?
use bignum; $foo = 12345.6789; $bar = $foo->copy()->bfround(0); $baz = $foo - $bar; print "what's wrong here? $baz\n"; $byhand = 12345.6789 - 12345; print "as expected $byhand\n";
... which does this:
what's wrong here? 0 as expected 0.6789
So the subtraction is getting zero, where I expected roughly 0.6789 also. And yes, I get the same thing if i use $baz = $foo->bsub($bar).
Any hints appreciated. Thanks!

Update - Thanks for the welcome; I've been lurking and annonning for years so it was prolly time. It was indeed a contamination of precision. When doing the bfround(0) you can Dumper the result and see it picked up a p=0 member, which got carried along after that. The bfround(0)->bfround(-5) solution works but I need to rtfm a couple more times to get my head around it. The problem I was trying to solve was merely, "what's the distance from this float to the nearest integer, wherever that is"

Replies are listed 'Best First'.
Re: bignum frustration
by SuicideJunkie (Vicar) on Aug 15, 2012 at 21:39 UTC
    use bignum; $foo = 12345.6789; $bar = $foo->copy()->bfround(0)->bfround(-5); $baz = $foo - $bar; print "what's wrong here? $foo - $bar = $baz\n"; $byhand = 12345.6789 - 12345; print "expected $byhand\n";
    Gives:
    what's wrong here? 12345.6789 - 12346.00000 = -0.32110 expected 0.6789
    Seems to me that the precision is propagated to the result value, and -0.32 rounds up to zero in your original example.
Re: bignum frustration
by Athanasius (Archbishop) on Aug 16, 2012 at 03:26 UTC

    Hello not_japh, and welcome to the Monastery!

    #! perl use strict; use warnings; use bignum; my $foo = 1_234_500_000_000_000_000_000_000.6789; my $bar = int $foo; my $baz = $foo - $bar; print 'baz = ', $baz, "\n";

    Output:

    baz = 0.6789

    Often, the simplest solution is also the best. ;-)

    Update: Added greeting.

    Athanasius <°(((><contra mundum

      How can you be >0.5 away from the nearest integer?

        Finding the nearest integer is still easy with just the int function:

        #! perl use strict; use warnings; use bignum; while (my $num = <DATA>) { chomp $num; print 'float = ', $num, ', nearest int = ', int ($num + 0.5), "\n" +; } __DATA__ 12345.6789 1_234_500_000_000_000_000_000_000.6789 10.49 11.5 12.500000001 1_234_500_000_000_000_000_000_042.499999 13

        Output:

        float = 12345.6789, nearest int = 12346 float = 1_234_500_000_000_000_000_000_000.6789, nearest int = 12345000 +00000000000000001 float = 10.49, nearest int = 10 float = 11.5, nearest int = 12 float = 12.500000001, nearest int = 13 float = 1_234_500_000_000_000_000_000_042.499999, nearest int = 123450 +0000000000000000042 float = 13, nearest int = 13

        :-)

        Athanasius <°(((><contra mundum