Using floating numbers for business arithmetics

Hello nat-world,

my customer has some problems with business arithmetics. Some numbers contain more than 7 decimals, others have a lot of integer digits. These numbers must be used together in arithmetic statements. As numbers with more than 7 decimals are not possible, these numbers are represented by packed integers and in calculations the factor 10**X is applied to shift the decimal point.

The results sometimes are rounded to zero or two decimal characters. You can imagine, if you have big numbers to multiply with small factors, each decimal digit in the factor is important for the result (financial application).

We are thinking about converting some or all amount fields to F8 to get the most precise result.

What do you think about this. Have you any experience about this?

PS: this question is also posted on SAG-L

Wilfried

Hi Wilfred
You should take care with floating point !
I once heard of a financial system based on floting points that after a year had rounding errors resulting in thousands of Euroes !

I couldn’t quite remember but I just checked that the MF floating point definition has (almost) 2^56 for the fraction ~=17 significant digits
and IEEE has only 2^52
(see http://en.wikipedia.org/wiki/Floating_point)

Meaning if you have huge number that ALSO has many decimals you’ll end up with something very different from what you expected - see below.

cheers Finn

DEFINE DATA LOCAL
1 P (P15.7) INIT <123456789012345.1234567>
1 P2 (P15.7)
1 F (F8)
END-DEFINE
MOVE P TO F
P2 := F
WRITE
'before ’ P /
'floating ’ F /
‘after move f -> p’ P2
END

  • and the sunny smiley was of course originally a
    Floating 8

Finn

Here’s my test… But I guess you have to do a proper test with your special algorithm.

define data local
01 #p (P22.7)
01 #f (F8)
end-define
for #p = 1.0000001 to 2 step 0.0000001
  #f := #p
  if #p ne #f
    display #p #f
  end-if
end-for
end

Just use the code-Tags to supress the smiley… Example:

[code]01 #f (F8)[/code]

Many many years ago (BA and BN, before Adabas and Natural), I worked almost exclusively with Fortran on scientific and engineering systems. The major problem we had with floating point was comparisons. Due to various numbers not being represented precisely by a specific number, a comparison between, say, #A and 10 * (#A/10) might not come out equal. We often resorted to testing within a “delta” which was typically a very small number.

That said, if you are applying factors (10**n) to numbers to control the decimal point, you should not be losing precision. Rounding to some number of decimal points should not be a problem if you have converted your numbers to integers (e.g. P29), unless you have some vary large numbers with lots of decimal points. Even so, twenty nine total digits of precision is quite a bit. Do you have more than this?

Thanks all for the replies. I analyzed Matthias’ example and my first shot from the hip was: don’t use floating. But then steve’s answer about comparison problems with floating extended this example.

In our application we do not compare the fields in question. We only need them for (rounded) calculations. The fields currently exist as (P8.7) in the database and changing them to float is easy. The programs only need to be recataloged after changing ddms and database files.

That will be all of the efford needed.

Thanks again!