If HashMap is a Dictionary with weak keys, then there could be GC
differences in 10.1 that will cause the object to be GC'd or not GC'd from
Interesting thought, but I don't think it applies here.
The 'object' (used as a key) is passed in as a parameter. If the hashMap does not already have the key, it proceeds to add two eventListeners to the object, and then adds it to the hashMap, setting the current value to 0. (That value will later be incremented as data is downloaded, and the progress is incremented by the downloader)
The adding of the eventListeners would have crashed had the object been null. Looking at it in the FlexBuilder 3 debugger, i can see that the 'data' and 'listData' elements are null (as expected), but that the 'source' element has the url that we expect to see there. Thus, the object cannot be null when it is added to the map at the end of the method.
FWIW, this class was written by an employee that left the company 5 years ago, a little before I joined. It has been used by all of us as a black box that worked flawlessly all this time. Only under 10.1 does it have trouble, and then only under IE, Chrome or Vista, still working fine in XP, Mac and Firefox.
Is there something in 10.1 that changes the way complex objects are added (or supported) in hashMaps?
I don't know which HashMap class you are using. I am unfamiliar with such a
I don't think you understood my explanation. If HashMap is a Dictionary
with weak reference keys, there has to be some strong reference to the
object in order to prevent it from being GC'd. I'm sure it wasn't null at
the time it was added, but it can be removed from the Dictionary at any time
if there isn't a strong reference to it. Attaching listeners to the object
does not create a strong reference to the object. Instead the object has
strong references to the listeners. Therefore, by your explanation, it is
quite possible that garbage collection is running more frequently in 10.1
and flushing objects from the HashMap sooner than you expected.
Well, if so, then you may have hit the nail again. Two for two. Wow!
I don't quite understand the difference between 'weak reference' and 'strong reference' though. I will try to Google it in the morning to see what I can learn, but if you have a quick explanation, it would definitely be appreciated.
Just got home from our first gig as The Professional Wedding Photographer. I am bushed...! Am currently importing 1100 images into Lightroom. I love Adobe products!
Most references are strong:
Foo.bar = someObject; // strong reference from Foo to someObject.
There are two ways to create weak refs: Dictionary and addEventListener.
The Garbage collection walks all strong references to see if anybody is
still using an object. It does not walk weak references.
Thanks. That sounds like it makes sense.
The last line in the method is:
loadingObj[object] = 0;
Here the 'loadingObj' is the hashMap, and the object is the key we are entering. It is an EventDispatcher.
So my question is: Does setting the value of the key'd entry to 0 create a strong reference? That is the value that we later increment as data comes in, until it reaches 100, at which point we emit a signal and explicitely remove the key.
If setting the value to 0 does not create a strong reference, do you have a suggestion of a simple line(s) we could add to force a strong reference key, and thus avoid any GC until we wish to explicitely remove the key?
Back in the office, looking at the code. I see now that HashMap is actually another legacy class of ours, probably written by that same ex-employee. It extends flash.utils.Dictionary.
Looking at the Adobe docs for Dictionary, I see there is an optional parameter for "
(weakKeys:Boolean = false)". Since we are not providing an argument when constructing the HashMap (and thus, the Dictionary), and the default is 'false', I believe that all keys are strong. That in turn, leads me to believe that our keys will not be garbage collected behind our backs, and should stay there until we explicitely remove them.
And thus the mystery remains as to why IE, Chrome and Vista show the key as null immediately after adding it (in the FlexBuilder 3 debugger) and work fine in Flash 10.0 on all platforms, and 10.1 on Firefox and Windows XP. (Note that the actual problem is that we crash upon trying to access the keys. The debugger is simply showing me that the problem exists instantly after adding the key)
Again, I don't know anything about your HashMap class. If it uses a
Dictionary and you don't want arbitrary collection of its contents, and you
have a way to clean up objects that are no longer wanted, then the
Dictionary should be instantiated to use strong reference keys.
The value assigned to the key does not affect the key's GC behavior unless
it is somehow a reference to the key itself.
What does the getKey method look like?
Problem is resolved... sort of...
I eliminated the HashKey class entirely, and just reference Dictionary directly, and the problem disappears. I don't see anything in the HashMap class code that would directly account for this, but right now we are getting thousands of user complaints daily, so "if it works, it is good enough..."
Consulting with another programmer at work, we came to possible conclusion that our use of the Dictionary through the intermediate class may have caused an ambiguity of the actual nature of the key we were using. An Image was passed to a method asking for an EventDispatcher -- inheritence should allow this, but perhaps there was an ambuguity that IE and Firefox (and XP vs Vista) interpreted differently.
At any rate, I can now return to the project I was supposed to be working for the past week. Another big release of two products in three weeks. Fun time in the Big City.
Thanks again for all your help on this!