Bill Tudor

Weblog

  Home  |   Contact  |   Syndication    |   Login
  49 Posts | 0 Stories | 95 Comments | 0 Trackbacks

News

Copyright © Bill Tudor

Archives

Post Categories

Static Reflection in .Net

Where have I been?

I recently took a few minutes to look through the latest MSDN magazine and ran across a nice article by Jeremy Miller on “Functional Programming for Everyday .NET Development”. The section titled “Lambdas as Data” was my first introduction to static reflection in .Net. Where the heck have I been? I don’t write database persistence code, so I am not familiar with NHibernate (or fluent NHibernate) (which is where Jeremy’s sample comes from), but I am still surprised at how little I understand about everything Linq brought to the .Net party. A quick search around the internet reveals this topic is well-covered, and several years old.

Example Code

Suppose you have a need to dynamically discover properties on an object. Easy, right? After all, that’s what the System.Reflection namespaces is for! However..

Let’s look at a class named “SomeObject” with a property “SomeProperty”:

class SomeObject
{
    public string SomeProperty { get; set; }
}

You can use so-called “static reflection” like this:

   1: class Program
   2: {
   3:     static void Main(string[] args)
   4:     {
   5:         SomeObject o = new SomeObject()
   6:         {
   7:             SomeProperty = "Test"
   8:         };
   9:         staticReflection(o, e => e.SomeProperty);
  10:         Console.ReadKey();
  11:     }
  12:     static void staticReflection<T>(T o, Expression<Func<T,object>> expression)
  13:     {
  14:         MemberExpression me = expression.Body as MemberExpression;
  15:         if (me != null && me.Member.MemberType == System.Reflection.MemberTypes.Property)
  16:         {
  17:             Console.WriteLine("Property: '{0}' of type '{1}' has value '{2}'.",
  18:                 me.Member.Name,
  19:                 expression.Body.Type,
  20:                 expression.Compile().Invoke(o)
  21:                 );
  22:         }
  23:     }
  24: }

The output is:

Property: 'SomeProperty' of type 'System.String' has value 'Test'.

Very cool. Now I need to understand why the second argument has to be something like Expression<Func<T, object>> rather than simply Expression<T>. If the latter is used, the compiler rewards me with:

Error    1    Cannot convert lambda to an expression tree whose type argument 'StaticReflection.SomeObject' is not a delegate type

It’s the whole “return type” thing on the delegate that throws me as well – where does that come from? In my code sample I have declared the Func return type as type “object” (it is actually a string in my case). Why don’t I have to do something like “e => {return e.SomeProperty;}”, and how come a lambda expression with a statement body like that cannot be converted into an expression tree (compiler’s words, not mine)?

I still have a little more learning to do before really understanding what’s going on here. My suspicion is that Linq brought a heck of a lot more to the party than it might appear at first look.

  • Share This Post:
  • Share on Twitter
  • Share on Facebook
  • Share on Technorati
posted on Monday, October 12, 2009 12:08 PM