Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations gkittelson on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Wierd multiplication/floating point bug?

Status
Not open for further replies.

AlienFetus

Programmer
Nov 14, 2001
2
CA
Hi,

The best way to demonstrate the problem is with this example:

1: $a = 2.01 * 100;
2: print $a,"\n";
// prints: 201
3: print int($a),"\n";
// prints: 200

Now, obviously, Perl is hiding some massive number of 9s after the decimal point at (2). But even though it should be a whole number after (1), it isn't. I know deep down this is due to some minor floating point inaccuracy, but can someone explain to me why Perl isn't handling 3 significant digits accurately? And is there any way to tell when this inaccuracy arises? I've noticed that 18.15 does the same thing, for example, and 18.31.

How do I resolve this except making sure I use the Math::Round module everytime I do arithmetic?

I am using v5.8.0 built for i386-linux-thread-multi, with locally applied patches:
MAINT18379

Thanks,
Don.
 
use integer;
and multiply your results by 1

search this forum for ishnid and integer

ish has a wonderful example of why stuff happens, most partic. this

--Paul

cigless ...
 
See the "Why am I getting long decimals" question in perlfaq4 for an explanation of why this happens. You'll find another explanation in this conversation I had with someone on another forum.

>> can someone explain to me why Perl isn't handling 3 significant digits accurately?
>> And is there any way to tell when this inaccuracy arises?
The number of significant digits is actually irrelevant. Any time you use floating point arithmetic, there's a high possibility that slight inaccuracies will be present (even a seemingly-simple number like 0.2 can't be accurately represented in binary). If you require absolute accuracy, you should probably work in integers (e.g. for money, deal in pence/cents/cent, rather than dollars/pounds/euro) and then introduce the necessary decimal point when displaying the number to the user.

In your code, change your first print statement to this:
Code:
printf "%.50f\n", $a;
That should help you understand what's going on. (Incidentally, using $a as a variable name isn't recommended, as it's a special variable name used in sorting. Just so you know).
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top