Author Topic: str$ handiling of negative float values  (Read 7193 times)

garysdickinson

  • Hero Member
  • Posts: 502
  • Old PLC Coder
    • View Profile
str$ handiling of negative float values
« on: January 14, 2015, 05:36:12 PM »
Hi all,

I was sort of surprised by the behavior of the str$(x#,w) function when x# was a negative value.  -3 can be displayed as -2!

This experiment was only run in the simulator in i-TRiLOGI V 7.03 build 6.  I did not run this code on actual hardware, sorry.

This is my test code:

' Display Float
'
i = -3
while (i < 4)
   i# = i
   print #2 "Value: ";i;         ' print integer value
   print #2 " "; str$(i#);      ' float with default formatting
   print #2 " "; str$(i#,-3);      ' float with 3 decimal points
   print #2 " "; str$(i#,0)      ' float rounded to nearest integer

   i = i + 1

endwhile
[/color]

This is what I saw:

Value: -3 -3.0000000 -2.999 -2
Value: -2 -2.0000000 -1.999 -1
Value: -1 -1.0000000 -0.999 0
Value: 0 +0.0 +0.000 0
Value: 1 +1.0000000 +1.000 1
Value: 2 +2.0000000 +2.000 2
Value: 3 +3.0000000 +3.000 3
[/color]

I checked the bit pattern of the floating point values and saw that they represented exactly -3, -2 and -1, but if I used the str$(x#, w) statement, the strings did not represent whole integer values.

The str$(x#,0) format, which is documented as "Rounded to the nearest integer" thinks that the closest integer to -3 is -2???  I sort of think that the nearest integer to -3 is actually -3.

Am I expecting too much?

Also another fun fact about TBASIC.  The following code will not work as expected:

for i = -3 to 3
   i# = i
   print #2 "Value: ";i         ' print integer value
next
[/color]

Oh, I expected that the code between the for and next keywords would be executed for values of "I" from -3 to 3...

Interestingly, "I" is initialized to &H0000FFFD which is not -3 (for a 32-bit signed integer).  This results in the initial value of "I" being greater than the limit value of 3, so the code between for and next keywords is not evaluated.  If "I" had been a 16-bit signed value then %HFFFD is -3.  I am guessing that for/next can only work with unsigned values between 0 and 32767.  I'm guessing that this is real old code "feature".

Best regards,

Gary D

« Last Edit: January 14, 2015, 05:50:23 PM by garysdickinson »

support

  • Global Moderator
  • Hero Member
  • *****
  • Posts: 3170
    • View Profile
    • Internet Programmable PLCs
Re:str$ handiling of negative float values
« Reply #1 on: January 14, 2015, 11:42:49 PM »
Thank you for the feedback and report.

For the Display Float issue, you are right that that STR$(n,0) seems to use "round up" instead of round to the nearest (negative) integer if n < 0 as per your report.

However, we tested with STR$(round(n)) and that does round to the nearest integer so we suggest using the ROUND(n) function if you want to display a rounded integer that may become negative.

For the loop index problem with negative number representation, that seems to affect only current TL7 simulator. This program fragment actually works properly when transferred to the Fx PLC. Also the same program fragment works properly on TL6 so this requires a bug fix to TL7 simulator.

[Edit 2015-1-17]: The cause of loop index mentioned above was caused by TL7 simulator not sign-extend a negative number to 32-bit during assignment, and hence when a negative number is assigned to a 32-bit integer variable it became a 16-bit unsigned positive number.  Only the simulator is affected. This bug is now fixed on iTRiLOGI version 7.03 build 07.
« Last Edit: January 17, 2015, 09:17:22 PM by support »
Email: support@triplc.com
Tel: 1-877-TRI-PLCS

garysdickinson

  • Hero Member
  • Posts: 502
  • Old PLC Coder
    • View Profile
Re:str$ handiling of negative float values
« Reply #2 on: January 15, 2015, 11:39:29 AM »
Thanks.

Round(x#) works with both positive and negative integers.  

This got me to thinking about str$(x#,n).  This statement works fine when x# >= 0.0 ...

I am using the following work around and avoiding negative floating values with str$(x#,n):


   ' print float with 2 decimal points of accuracy
   '
   if (i# < 0.0)
      A$ = str$(-i#,-2)
      A$ = "-" + mid$(A$,2,len(A$)-1)   
      print #2 " "; A$
   else
      print #2 " "; str$(i#,-2)
   endif

[/color][/font]

This gets me "-2.00" when the floating value is -2.0.

Best regards,

Gary D.
« Last Edit: January 15, 2015, 11:48:34 AM by garysdickinson »

garysdickinson

  • Hero Member
  • Posts: 502
  • Old PLC Coder
    • View Profile
Re:str$ handiling of negative float values
« Reply #3 on: January 15, 2015, 12:55:02 PM »
One more thing about str$(x#,n) and iTRILOGi 7.03:

If the first argument is an integer value and not a float, it will compile without error, but the simulator will fail, also without error, at the line of code.

This will compile, but the simulator fails without an error message on the line of syntactically incorrect code:


i = 3                 ' executes
print #2 str$(i,-2)   ' breaks the simulator without an error message
[/font][/color]

Gary D.

support

  • Global Moderator
  • Hero Member
  • *****
  • Posts: 3170
    • View Profile
    • Internet Programmable PLCs
Re:str$ handiling of negative float values
« Reply #4 on: January 17, 2015, 07:24:14 PM »
Thanks again for the report.

STR$(n, d) function handles the execution differently when n is an integer and when it is a float variable or number (the two number types are represented differently internally).

Negative d is not defined when n is an integer and on the simulator it did cause a Java exception and the simulator aborted (if you run the TL7.bat you will see the error message on the console window). However, this cannot generate a compile time error since the n and d could be an expression instead of a single variable or constant.

On the Fx PLC if this is executed it simply returns a string with 11 zeros "00000000000" which was a result of bad parameters (negative d with n== integer).

It would probably make sense to convert the integer to float if STR$(n, d) encounters d <= 0 and apply the same formatting to the resulting float number. We will look into implementing this in the future release.
« Last Edit: January 18, 2015, 05:02:10 AM by support »
Email: support@triplc.com
Tel: 1-877-TRI-PLCS

garysdickinson

  • Hero Member
  • Posts: 502
  • Old PLC Coder
    • View Profile
Re:str$ handiling of negative float values
« Reply #5 on: January 17, 2015, 10:36:22 PM »
Excellent.  The expaination makes sense.  I made the wrong guess as to the actual problem.  The issue is with the field width parameter in the str$(v,n),n being less than 0 when the value, v, is an integer type.

Thanks for looking at this stuff.

Gary d