2

This comparison prints '0'b. Don't understand why... As I know strings are converted automatically to float in PL/I if needed.

put skip list('-2.34e-1'=-2.34e-1);
Bill Woodger
  • 12,968
  • 4
  • 38
  • 47
zer_ik
  • 410
  • 1
  • 4
  • 14
  • 1
    What output were you expecting? Is that the exact, as in pasted form the emulator, output you received? – Bill Woodger Jan 19 '17 at 17:00
  • @BillWoodger I was expecting '1'b – zer_ik Jan 19 '17 at 18:27
  • What is your environment? PL1F under Hercules? PL/I Optimizing Compiler? Another implementation of PL/1 such as the ancient Digital Research CP/M 80 compiler? – zarchasmpgmr Jan 19 '17 at 23:35
  • @zarchasmpgmr I am begginer and don't know. But I am working on really mainframe, not hercules emulator – zer_ik Jan 20 '17 at 11:15
  • @zer_ik I did some more research and reworked my answer. See if it explains the problem so you can understand it, else feel free to ask for clarification in the comments. – piet.t Jan 20 '17 at 13:10

1 Answers1

4

I have tested this in our environment (Enterprise PL/I V4.5 on z/OS) and found the same behaviour - under certain compile-options.

Using the option FLOAT(NODFP) (i.e. do not use native support for decimal floating point, I think the option was introduced with Enterprise PL/I V4.4) the following happens:

  • the literal -2.34e-1 is converted to its internal representation as bin float(6), i.e. short binary floating point
  • the literal '-2.34e-1' is compared with a bin float(6) value, so it has to be converted to a bin float as well
  • since -0.234 does not have an exact representation as a binary fraction it seems the compiler converts it to a bin float(54), i.e. an extended binary floating point value, to get maximum precision.
  • So since -0.234 has an infinite number of digits after the decimal point in its binary representation but the two converted values preserve a different number of digits the values do not compare equal.

Under FLOAT(DFP) (i.e. when using the machines DFP support)

  • the internal representation of the literal -2.34e-1 is an actual decimal floating point and thus exact
  • as is the representation of '-2.34e-1'
  • so under this compile-option both compare equal and the output of your program is '1'b

So your problem is a combination of the compilers different choice of data-representation and resulting rounding-errors from using binary floating point of different precision.

piet.t
  • 11,718
  • 21
  • 43
  • 52
  • This demonstrates one of the pitfalls of floating-point value equality comparison. @piet.t thank you for performing the test compilations. By any chance, did you turn on the LIST option and look at the generated code? – zarchasmpgmr Jan 20 '17 at 18:34
  • Thank you a lot! The problem turned up complicated enough. I thought the answer would be much easier. – zer_ik Jan 21 '17 at 10:40