Attempting to solve the INotifyPropertyChanged problem
So I have made an attempt at solving the INotifyPropertyChanged problem.
This project can be found here https://github.com/SimonCropp/NotifyPropertyWeaver
When I mention this to friends the first response is often "Why? The problem has already been solved"
So why attempt to solve a problem with so many solutions?
Well let’s look at the available solutions (not meant to be a complete list)
String constants
The traditional approach recommended by Microsoft. http://msdn.microsoft.com/en-us/library/ms229614.aspx
Issues
- Can’t use automatic properties
- Results in bloat in source code. Approx. 10 line compared to 1 for automatic properties
- The risk of the string not being correct.
- Require you to hand code the notify code for each property
Helpers to Avoid string constants
There are all kinds of solutions floating around that help you avoid using property names as strings. These methods use a combination of Lambda expressions, reflection and stack walking.
http://blogs.microsoft.co.il/blogs/dorony/archive/2007/08/31/WPF-Binding2C00-INotifyPropertyChanged-and-Linq.aspx http://www.timvw.be/little-inotifypropertychanged-helper/
Issues
- Performance implications
- Requires you to write code. It depends on your choice of technology but a full solution can be achieved in around 30 lines of code
- Some implementations require a base class
- Excluding having a property name as a string has all the other issues as the String Constant approach
Code Generation
This involves using an IDE addin to inject the raw code for you. There are many implementations available using T4 Templates and Resharper to name a few.
http://koder.wordpress.com/2010/03/25/resharper-inotifypropertychanged/ http://www.scottlogic.co.uk/blog/colin/2009/08/declarative-dependency-property-definition-with-t4-dte/
Issues
- Has all the same issues of string constants except having to hand code the property notification
Run-time Proxy
This approach involves emitting IL at runtime. This IL creates a proxy inheriting from your model that facilitates property interception. This can be done using Castles Dynamic Proxy,
http://ayende.com/Blog/archive/2009/08/07/nhibernate-amp-inotifypropertychanged.aspx
Issues
- Performance implications
- Requires an assembly reference
- Requires you to write approx. 100 lines of code
- Since you need to use a runtime factory to create your proxies you cannot use object and collection initializers
- There are some complexities involved in creating proxies for nested objects
PostSharp (Community version)
PostSharp is a compile time weaving tool that greatly simplifies injecting IL into an assembly.
Issues
- Performance implications
- Requires an assembly reference
- Requires the pollution of your code with attributes
- PostSharp is a general solution not targeted at solving this problem. Hence you still need to implement the injection code. Not too difficult at 40 lines of code
- Results in assembly bloat
It is an intentional limitation of the community version that it does not optimise the injected code. So in effect this results in 150 lines of code being injected into each property. Do the math on a large number of classes and your assembly size rapidly increases. http://www.sharpcrafters.com/forum/Topic4578-23-1.aspx
A note on “Performance issues”
There is no arguing that many of these approaches are slower and uses more memory than using a string constant. It could also be argues that this performance overhead is significant when compared to a simple property set. In reality performance is a non issue. If you are using INotifyPropertyChanged it is for the purpose of databinding to a UI. These approaches may add milliseconds to a property set which will not be noticeable to the user.
What I aim to build
So I guess I wanted a solution with the following
- No attributes required
- No need for an assembly reference
- Minimal impact on performance
- Minimal impact on memory
- No need to hard code property names
- Support for property and collection initializers
- No base class required
- Support for Automatic properties
- Not require the user to write code
- No unnecessary assembly bloat
And I would like to think I am close to achieving all these points.
Have a play and give me some feedback.
https://github.com/SimonCropp/NotifyPropertyWeaver
Edit
I think I was overly critical of PostSharp above. I am looking at solving a very specific problem with some very fine grained AOP. PostSharp is a very powerful tool that enables a whole range of cool AOP capabilities. It should not be judged or disregarded based on its handling of one problem.
No new comments are allowed on this post.
Comments
No comments yet. Be the first!