Today I received a bug report. When I took a closer look at the bug, I realized that I used x.contains() method where x is a CF array. The code needs to determine if an integer is in the array x, and the java contains() method does exactly what I need. (FYI: CF array == java.utils.Vector)
However, since the array is from JSON, hell breaks loose...
<cfset a = [0,1,2]>
<cfset json = serializeJSON(a)>
<cfset b = deserializeJSON(json)>
<cfdump var="#a.contains(0)#">
<cfdump var="#b.contains(0)#">
You would think both cfdump will give you "YES", but they do NOT!
YES NO
Why? if you try it you'll find that after serialized and deserialized to and from JSON, the array actually became [0.0,1.0,2.0] ! You may verify with #d.toString()# if you don't believe me.
So... how do I continue to use contains()? You would think
b.contains(javacast('double',0))
...and this finally returns 'YES'.
However, since my code need to work with both [0] and [0.0], I ended up writing the contains function in CFML instead with <cfloop> and <cfif>.
I thought I would save time by calling underlying java method, but I actually ended up spending more time fixing this 'bug'... For those who use underlying java methods in CF, watch out! Especially when you use JSON!

2 comments:
very useful to know. I'd assume the same thing holds true for other collections methods (indexOf(), etc).
thanks Henry. good stuff.
Although I will occasionally use the underlying java methods of a ColdFusion variable, I tend to shy away from doing that because they're not documented, or supported. I also shy away from it because the underlying Java tends to be more complicated than the CF equivalents. In this case the source of the problem is really the JSON serializer, but I would think this would work:
str = "," & ArrayToList(jsonArray) & ",";
hasZero = reFind(",0(\.0*)?,",str);
If you know that there won't be values less than zero in the array it becomes even easier:
hasZero = ArrayMin(jsonArray) eq 0;
Post a Comment