Skip to main content
Participant
September 30, 2011
Question

Hidden Special Characters in Variable

  • September 30, 2011
  • 2 replies
  • 1648 views

I am having a weird issue and for the life of me cannot figure out the root cause.  I have a query that is pulling back some data including a summed money data type from sqlserver called totalAmount.  We are looping over these rows and adding up some totals of the rows such as:

<cfset myAA = 0 />

<cfset myAB = 0 />

<cfloop ... >

<cfif ... >

<cfset myAA = myAA + getPayments.totalAmount />

<cfelse>

<cfset myAB = myAB+ getPayments.totalAmount />

</cfif>

</cfloop>

At this point we add the 2 together...

<cfset mySum = myAA + myAB />

We are expecting this to be 0, but in one instance it is not so, even though it should be.

Outputting the two variables gives them as -75.03 and 75.03.  When these are added together the result is:

-1.05160324892E-012

If I do a trim like:

<cfset mySum = trim(myAA) + trim(myAB) />

It returns 0.  So it seems there is an additional character on one or both of those variables, but what is it and where is it coming from?  If I output:

(#myAA#) + (#myAB#)

I get (-75.03) + (75.03).  So no whitespace... If I do a len() on each I get 6 and 5.

If I do a compare such as #myAA# => #(myAA eq "-75.03")#

I get -75.03 => NO, same with the other.

So I am dumbfounded, it seems there is a control character there that is hidden and throwing this off.  Anyone have any suggestions on what to check or any ideas what the problem may be?  I would rather fix the problem at the root rather than throwing trim() around variables that should be numeric to begin with.

-Shawn

    This topic has been closed for replies.

    2 replies

    Participant
    October 3, 2011

    Thanks both of you for your responses.  I think my main confusion of all this came when using trim() on the numbers and that "fixing" the issue. That made me lose sight of what was really going on behind the scenes.  I will keep all of this in mind when working with floats. 

    Thanks again for the help.

    BKBK
    Community Expert
    Community Expert
    September 30, 2011

    There is actually no problem at all. The expression -1.05160324892E-012 is the so-called Scientific Notation for 0.0000000000010516032....

    ColdFusion has simply converted -75.03 and 75.03 internally to a high number of decimals(for more precision). By default, ColdFusion holds a decimal value internally as a double, a decimal value to an arbitrary level of precision. Hence 75.03 may be held in memory as 75.0300000000012345, whereas -75.030000000088888.The result of adding them is a very small number, almost 0, but not quite 0.

    If you wish to avoid the Scientific Notation, then use the function decimalFormat.

    Inspiring
    September 30, 2011

    As BKBK correctly alludes to: this is expected behaviour for floating point

    operations.

    To avoid it, use precisionEvaluate(). This will convert the numbers to

    BigDecimals instead of Doubles, and you'll see expected results.

    --

    Adam

    Participant
    September 30, 2011

    Thanks for the responses.  The part I do not understand is if Coldfusion is converting the number to high number of decimals, why is it not padding with all 0s.  I am adding numbers together that have at most 4 decimal places.  Anything after the 4th decimal place should be a 0.  If coldfusion stores these numbers as something other than 75.03 why not disply the full number when I output it? 

    Also why does trim() fix the issue?