I think this is abusing anonymous types,
dynamic and extension methods.
These things are very useful in LINQ; they allow you to define a type on-the-fly to hold groupings (with the
GroupBy method), for example. Anonymous types should only live within a method, and not leak outside of it - this means returning an anonymous type is bad, see this Jon Skeet answer on Stack Overflow.
Don't get me wrong:
dynamic is awesome. But whenever I encounter it, I do everything I can to "contain" it and get back into compile-time strongly-typed code. The reason is that whatever it touches becomes
dynamic as well, making more and more code that's not resolvable at compile-time. Use with caution.
System.Object, which means literally anything in the Wonderful World of .NET can be passed to your method, and now has a
ToExpando1 method: extending anonymous types just isn't right, these things are meant to be temporary, on-the-fly objects. If you need first-class citizens, create a new class.
Note: this is all based on not knowing how this extension method is being used! Based on comments however:
I am using the method to convert anonymous objects to ExpandoObject so that they can be accessed in Views [...]
This might make sense. I don't do enough Web development to be a reference on the matter, but it seems to me that the model accessed by a view would be much better off as a full-fledged class, instead of just a bag of properties glued together into an anonymous/dynamic type.
I don't like the naming style:
public static dynamic ToExpando1(this object AnonymousObject)
Why there is a 1 there isn't clear to me (looking at the post's edit history is instructive though - thanks for making that edit!). Also
AnonymousObject being a local-scope parameter, should be named
anonymousObject, and having
Object in an object's name just doesn't feel right. How about
public static dynamic ToExpando(this object that)
In the method's body, you're declaring
expando as an
IDictionary<string, Object> expando = new ExpandoObject();
It's not clear why
System.Object isn't referred to as its language alias
object (as it is in the method's signature), but since you're casting
dynamic before returning it, I don't see why you can't be just declaring it with
var expando = new ExpandoObject();
The method uses
System.Reflection types correctly, I like that.
Why your original LINQ code didn't work
As @Sandeep has suggested, the correct usage of LINQ is to project a selection using the
Select method, like this:
.Select(p => new KeyValuePair<string, object>(p.Name, p.GetValue(anonymousObject));
What your original code does, had side-effects (assigning a value into an array index) - LINQ stands for Language-INtegrated Query, querying objects isn't something that should have side-effects, hence assigning
expando[property.Name] can't work in a