Internet PLC Forum

General => Technical support => Topic started by: nealbert on February 18, 2019, 03:26:21 PM

Title: Perplexed by puzzling parentheses pecualiarity
Post by: nealbert on February 18, 2019, 03:26:21 PM
I'm not sure if this is a bug or a feature, but I'll throw it out there for your consideration....

In my FMD88-10 I have a Custom Function that takes an incoming analog voltage, scales it and converts the voltage to a temperature.  The last step in my CF is to convert the temperature from degrees C to degrees F using the commonly known equation:

F = (C * (9/5)) +32

Great, right?  WRONG!  The unnecessary pair of parentheses around the "9/5" causes the TBasic to yield an incorrect answer.
At room temperature (25C), the above equation yields and answer that's 17F degrees low.  At a temperature of 200C, the answer is over 150F too low.

What I know is...
So, the question is... why does TBasic yield an incorrect answer when unnecessary "()" are there?  Shouldn't it just ignore them?
Title: Re:Perplexed by puzzling parentheses pecualiarity
Post by: garysdickinson on February 19, 2019, 04:36:25 AM
Integer math and operator precedence is the answer to your perplexity.

9 divided by 5 is 1 with integer math.

Your spreadsheet and your calculator are doing floating point math. 9 divided by 5 is 1.8 with floating point math.  That is why the results are different then when you use a spreadsheet or a calculator.

Operator precedence.  The parenthesis in your expression:

     F = (C * (9/5)) +32

Forces TBASIC to perform the 9/5 division first.  Remember that 9/5 is 1.  The next thing TBASIC does is multiply the value of C by 1. Then TBASIC adds 32 and finally will assign the results of the arithmetic expression to the variable F.

I do not know how smart TBASIC's expression parser is.  If it was really smart it would, at compile time, precompute that the division of the constant subexpression 9/5 to be 1 and not actually do a division at run time. If may, also, recognize that the multiplication of the variable C by 1 is always the value of C.  TBASIC could simplify your expression to this because this is exactly what you wrote:

  F = C +32
Rule #1 for integer math is to do all your additions and multiplications first.  Do your division last to preserve accuracy.

You might want to rethink how you are converting an ADC value to temperature in F.  if you need F go from ADC units directly to F.

I would used scaled integer values.

I would, also, oversample the ADC so that I are working with a 14 bit ADC value rather than the advertised 12 bit value.

Gary D*ckinson
Title: Re:Perplexed by puzzling parentheses pecualiarity
Post by: garysdickinson on February 20, 2019, 11:01:04 AM
Neal,

I suggest that you try this equation to convert from C to F:

     F = (C * 9) / 5 + 32

That equation just forces the multiply before the division operation.  It gets you more accurate results when you are limited to integer math.

This is my spreadsheet results comparing doing the conversion with floating point vs. integer math:

C   F Float   F Integer   Error %
0   32.0           32           0.000
1   33.8           33           2.424
2   35.6           35           1.714
3   37.4           37           1.081
4   39.2           39           0.513
5   41.0           41           0.000
6   42.8           42           1.905
7   44.6           44           1.364
8   46.4           46           0.870
9   48.2           48           0.417
10 50.0           50           0.000

If you can tolerate the size of the errors then your are good to go!

Best regards,

Gary D* ckinson
Title: Re:Perplexed by puzzling parentheses pecualiarity
Post by: support on February 21, 2019, 12:16:14 PM
Thanks Gary for the formula.

To increase precision you can use a fixed point format

F = C*90/5 + 320

The result will be expressed in 0.1 degree F.

E.g. C = 22 degree

F = 22*90/5 + 320 = 716  = 71.6 degree F.
Title: Re:Perplexed by puzzling parentheses pecualiarity
Post by: nealbert on March 06, 2019, 01:37:21 PM
Gary, et al,

Thanks for the explanation.  I totally forgot I'm working with Integer math.

The conversion equation works fine without the extra parentheses and the client is happy now.

I'll keep in mind the methods you describe to increase accuracy.  I may need that some day.

Thanks again,
Neal Cooper
Title: Re:Perplexed by puzzling parentheses pecualiarity
Post by: garysdickinson on March 07, 2019, 11:19:21 AM
Neal,

I am glad that you were able to get the PLC firmware sorted out for your client.

Please feel free to contact me if you have questions with how to get the most out of these PLCs.  My email address is in my profile on the forum.

Thanks,

Gary D*ckinson