2
Vote

Indexing by hashcode

description

In Interactions.cs, you have a static dictionary that indexes by hashcode. Hashcodes aren't guaranteed to be unique, which is why you should normally index by the object itself (Dictionarys are built to handle hash collisions) - otherwise you'll get some
strange behavior in your behaviour very very occasionally.

comments

localjoostnl wrote Apr 11, 2012 at 5:36 PM

The comment is valid, but if you used the object themselves as indexes, than the collection has a STRONG reference to the objects, thereby defining it's whole purpose. I'd choose 'strange behavior in your behaviour very very occasionally' over 'memory leaks guaranteed' ;-)

onovotny wrote Oct 7, 2012 at 9:45 PM

Can't you work around this by using a closure?

Something like this:

newList.CollectionChanged += (s, e) => OnBehaviorsCollectionChanged(s, e, newList);

The generated closure will be rooted by the delegate instance in the newList CollectionChanged event. When newList goes away, then the closure won't be rooted and will be taken away as well.

With that, you avoid the need for the dictionary of WeakReferences.

onovotny wrote Oct 7, 2012 at 9:50 PM

Oh, and if you need to store the delegate so that you can unsubscribe, here's what I've done in the past:

Create a readonly attached property of type CollectionChangedEventHandler to store the delegate.

So it's something like this:

var handler = (s, e) => OnChanged(newlist);
obj.SetValue(OnCollectionChangedProperty, handler);

If/when you need to unsubscribe, you can simply do obj.GetValue() to get the handler then do oldList.CollectionChanged -= handler;

With that pattern, you hold on to the delegate reference and don't need weak dictionary references.

wrote Oct 7, 2012 at 9:50 PM

onovotny wrote Oct 7, 2012 at 9:55 PM

There's a few examples in the WebBrowserUtility class here:
http://mishrareader.codeplex.com/SourceControl/changeset/view/99918#1907767

Look at the OnNavigatingCommandChanged stuff

wrote Feb 14, 2013 at 6:52 PM