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

Gentlemen, Can you please help me understand why this calculation is coming out to be wrong? I was expecting int (42435.3408/411.9936) as 103. Perl prints the result is 103 but when used int function on the result it is getting 102!! Here is the code to reproduce the issue... $i = (42435.3408/411.9936); $j = $i; $k = int $j; $l = int(103); print "$i, $j, $k, $l\n"; It prints 103, 103, 102, 103 Should the value of $l be 103? If I use pragma integer (use integer;) at the top then all varaibles are showing 103. I wanted it to be 103 without having to explicitly 'rounding'. Thanks for the help. -Anju
  • Comment on Why the Integer part of this calculation is 102?

Replies are listed 'Best First'.
Re: Why the Integer part of this calculation is 102?
by moritz (Cardinal) on Mar 22, 2010 at 21:16 UTC
    $ perl -e 'printf "%.20f\n", 42435.3408/411.9936' 102.99999999999998578915

    This is smaller than 103, so int rounds down to 102. You'll have to use proper rounding.

    Perl 6 - links to (nearly) everything that is Perl 6.
      Thanks for the quick response on my issue! I am still confused, sorry! But wouldn't we get exactly 42435.3408 when we multiply 411.9936 * 103? Is the internal representation of 42435.3408 is different in perl?

        Both 3408/10000 and 9936/10000 are periodic numbers in binary, just like 1/3 is a periodic number in decimal. It would take infinite storage to store them as floats, so they're not being stored exactly.

        You can avoid the problem by using sprintf("%.0f", $x) (rounds) instead of int($x) (truncates).

        Others have answered you already; I just want to add that in Perl 6 your code does what you expect. It achieves that by storing decimal numbers as fractions/rationals internally.
        $ perl6 > say (42435.3408).perl 26522088/625 > say (42435.3408).WHAT Rat() > say 42435.3408 / 411.9936 103 > printf "%.20f\n", 42435.3408 / 411.9936 103.00000000000000000000
        Perl 6 - links to (nearly) everything that is Perl 6.