I suspected that this was the intentional behavior of the function. For what I am trying to do, I don't think "banker's rounding" will work. Not being a "real" programmer, perhaps I am approaching my problem from the wrong angle.
I am writing a script that works with a piece of CAM software to create a drawn pattern. The total number of patterns I need will vary each time the program is run, but the number will always be an integer. The trouble is that I have to alternate the patterns from the left side of the design to the right side of the design. When I have an even number of patterns, this isn't a problem. $ patterns means two patterns on the left and two on the right. The rule I must follow for odd numbers is to divide by two, round up to the next highest number, and put the higher number of patterns on the left. So for 5 patterns, I would have 3 on the left and two on the right. What I am trying to do is to get the number of patterns, divide by two, round up, then subtract this value from the total to obtain the right and left numbers. So in my case I always want to round up. Unless there is a better way to approach a problem like this.... Thanks for the help and the info. It helps a novice programmer such as myself to understand things a bit better. .-. --.. -----Original Message----- From: zsdc [mailto:[EMAIL PROTECTED] Sent: Tuesday, February 24, 2004 2:29 PM To: Zielfelder, Robert Cc: Perl Beginners List (E-mail) Subject: Re: Rounding of floating point numbers Zielfelder, Robert wrote: > One other odd thing I noticed using the sprintf method: > If $var is odd, $var2 rounds low. If $var is even, then $var2 rounds high. > Being a programmer by necessity rather than by choice forces me to take the > easy way out and use the POSIX solution to get the program written. > Although, it would be interesting to know why the sprintf method behaves the > way it does... Didn't you mean the other way around, i.e. rounding to the nearest even integer, instead of odd as you wrote above? It's a banker rounding, an old way of rounding numbers used even in times when bankers were doing it manually. It's a way to ensure that your results are not skewed in any particular direction, to minimize the accumulation of rounding errors after adding numbers together. When the fraction part is exactly 0.5, i.e. it's equally far from both integers it is between, then it rounds to the even one. Why even and not odd? Only because it's easier to divide by 2 without introducing more errors. Run this program: #!/usr/bin/perl -w for $f (.49, .50, .51) { for $i (0..5) { printf "%.2f -> %.0f\n", $i + $f, $i + $f; } } __END__ It will print: 0.49 -> 0 1.49 -> 1 2.49 -> 2 3.49 -> 3 4.49 -> 4 5.49 -> 5 0.50 -> 0 1.50 -> 2 2.50 -> 2 3.50 -> 4 4.50 -> 4 5.50 -> 6 0.51 -> 1 1.51 -> 2 2.51 -> 3 3.51 -> 4 4.51 -> 5 5.51 -> 6 Numbers with .49 are always rounded down (like with floor) to get the nearest integer, numbers with .51 are always rounded up (like with ceil) -- still, no problem with finding the nearest integer -- but numbers with .50 not having a nearest integer, are rounded to the nerest even integer. This not Perl-specific at all. This C program: #include <stdio.h> int main() { float i, f; for (f = 0.49; f <= 0.51; f += 0.01) for (i = 0; i <= 5; i++) printf("%.2f -> %.0f\n", i + f, i + f); return 0; } /* END */ prints exactly the same output as the above Perl program. I haven't read everything in this thread so I don't know what results are you exactly expecting, but I think that you probably should use Math:: modules, like Charles suggested. Do you want numbers with decimal part .5 to always round up? Keep in mind that it will skew your results. See this program: #!/usr/bin/perl -w use POSIX qw(floor ceil); sub round1 { sprintf '%.0f', @_ } sub round2 { $x = shift; $r = floor($x); if ($x - $r >= 0.5) { $r = ceil($x) } return $r; } for (1..10000) { $x = 0.1 * int rand 100; $sum += $x; $rsum1 += round1($x); $rsum2 += round2($x); } printf "Real:\t%.1f\n", $sum; print "Banker:\t$rsum1\n"; print "5up:\t$rsum2\n"; __END__ The function round1() rounds just like printf and the function round2() rounds .5 always up. The program adds random numbers between 0.0 and 9.9 and prints the real sum and the sums of numbers rounded with both methods. See that the second one is always considerably larger. Every rounded number is skewed up by 5% on average. This is exactly why we use banker rounding. -- ZSDC -- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED] <http://learn.perl.org/> <http://learn.perl.org/first-response>