WinBatch® Technical Support Forum

All Things WinBatch => WinBatch => Topic started by: chrislegarth on October 02, 2022, 09:17:23 PM

Title: -0.00 Sum
Post by: chrislegarth on October 02, 2022, 09:17:23 PM
I have an odd thing I have encountered when adding a list of numbers with the resulting sum being -0.00.
I'm able to get the same -0.00 when adding negative numbers or subtracting positive numbers.

When I subtract 31.24 partway through the list the result is 0.00 as I expected.

Thoughts on the -0.00?  Is this expected?

Code (winbatch) Select

decimals(2)
amount = 0
amount = amount + 12.01
amount = amount + 12.90
;amount = amount + -24.91
amount = amount - 24.91
amount = amount + 13.15
amount = amount + 14.60
amount = amount + 3.67
;amount = amount + -31.42
amount = amount - 31.42
amount = amount + 2.28
amount = amount + 2.24
;amount = amount + -4.00
amount = amount - 4.00
amount = amount + 2.61
amount = amount + 2.26
amount = amount + 1.25
amount = amount + 1.23
amount = amount + 1.28
amount = amount + 1.25
;amount = amount + -10.40
amount = amount - 10.40
message("",amount)



Title: Re: -0.00 Sum
Post by: td on October 02, 2022, 10:52:55 PM
Is there an issue here? After all -0.0 == 0.0.

{edit} Should have mentioned that you will get a different result when you remove the "decimal(2)" line. The full floating point result is a very small negative number.
Title: Re: -0.00 Sum
Post by: chrislegarth on October 03, 2022, 07:40:57 AM
It is just a display issue as the numbers represent currency and no one expects to see -0.00.
I guess I'm just wondering why the last operation results in a tiny negative number when the others do not.

Sum Output
12.01
24.91
0.0
13.15
27.75
31.42
0.0
2.28
4.52
0.52
3.13
5.39
6.64
7.87
9.15
10.4
-1.77635684e-015
Title: Re: -0.00 Sum
Post by: td on October 03, 2022, 11:28:38 AM
You would need to have a basic understanding of how floating point numbers are represented on binary systems to effectively answer that question. Basically, real numbers have values that fall between two digits in binary systems. It would take an infinite number of bits to accurately represent all real number between two integers. This leads to representational errors that are not just an issue for WinBatch. This is an issue common to all computers using  IEEE 754 standard based floating point number machine instructions.

In the standard "Zero is a special value denoted with an exponent and mantissa of 0. -0 and +0 are distinct values, though they both are equal."
Title: Re: -0.00 Sum
Post by: td on October 03, 2022, 01:13:09 PM
A quote from this paper https://docs.oracle.com/cd/E19957-01/806-3568/ncg_goldberg.html (https://docs.oracle.com/cd/E19957-01/806-3568/ncg_goldberg.html) that explains it much better than I can:

"Squeezing infinitely many real numbers into a finite number of bits requires an approximate representation. Although there are infinitely many integers, in most programs the result of integer computations can be stored in 32 bits. In contrast, given any fixed number of bits, most calculations with real numbers will produce quantities that cannot be exactly represented using that many bits. Therefore the result of a floating-point calculation must often be rounded in order to fit back into its finite representation. This rounding error is the characteristic feature of floating-point computation."
Title: Re: -0.00 Sum
Post by: kdmoyers on October 03, 2022, 01:18:57 PM
This is fun: go to https://www.h-schmidt.net/FloatConverter/IEEE754.html
and type in some of your values.  I was amazed.  No wonder banks and such
try not to store money values in floating point numbers.
Title: Re: -0.00 Sum
Post by: ChuckC on October 03, 2022, 04:42:57 PM
Why am I reminded of this?

https://filmschoolrejects.com/getting-rich-with-richard-pryors-banking-scheme-from-superman-iii-7811840a8a0/ (https://filmschoolrejects.com/getting-rich-with-richard-pryors-banking-scheme-from-superman-iii-7811840a8a0/)

Title: Re: -0.00 Sum
Post by: td on October 05, 2022, 04:50:06 PM
Quote from: chrislegarth on October 03, 2022, 07:40:57 AM
It is just a display issue as the numbers represent currency and no one expects to see -0.00.
I guess I'm just wondering why the last operation results in a tiny negative number when the others do not.

Sum Output
12.01
24.91
0.0
13.15
27.75
31.42
0.0
2.28
4.52
0.52
3.13
5.39
6.64
7.87
9.15
10.4
-1.77635684e-015

Should have mentioned that to remove the "-" sign from a the 0.00 result is to do something like this
Code (winbatch) Select
if amount == "-0.0"
   amount = StrClean(amount, "-", "", 0, 1)
endif


Using a string for the minus zero value for the right-hand side causes the amount value to be rounded before the comparison is made. Of course, the rounding is the result of the Decimals function.
Title: Re: -0.00 Sum
Post by: chrislegarth on October 07, 2022, 08:03:18 PM
Thanks Everyone!

Tony- I did something similar to handle it that seems to work as well.

Code (winbatch) Select
if amount == -0.00 then amount = 0.00
Title: Re: -0.00 Sum
Post by: stanl on October 08, 2022, 05:39:51 AM
Quote from: ChuckC on October 03, 2022, 04:42:57 PM
Why am I reminded of this?

https://filmschoolrejects.com/getting-rich-with-richard-pryors-banking-scheme-from-superman-iii-7811840a8a0/ (https://filmschoolrejects.com/getting-rich-with-richard-pryors-banking-scheme-from-superman-iii-7811840a8a0/)


Good movie. Actually worked with a Commission program where certain calculations would be a penny off due to rounding error. I guess a more general question would be: if values were placed in Currency Type Object would the results still be the same as the floating point numbers the OP presented that created the issue?
Title: Re: -0.00 Sum
Post by: td on October 09, 2022, 06:39:26 AM
Quote from: chrislegarth on October 07, 2022, 08:03:18 PM
Thanks Everyone!

Tony- I did something similar to handle it that seems to work as well.

Code (winbatch) Select
if amount == -0.00 then amount = 0.00

Just remember that the Decimal function does not change the actual value of the amount variable in your example. It only changes the displayed value when the variable is converted to text.