Eric Yin
Eric Yin

Reputation: 8973

Select object by literal text name in Linq

Consider this is a standard Linq

from q in SomeQuery select new SomeObject { SomeKey = q.SomeKey }

What if the Somekey is a text I got from other place, then the code like this is not going to work

string key = "SomeKey";
from q in SomeQuery select new SomeObject { key = q[key] }

I hope you got my idea. Please tell me a correct way to write Linq, when I know the property by a text string.

Upvotes: 4

Views: 1177

Answers (2)

Jon
Jon

Reputation: 437336

In the general case you are looking for something like

var key = "SomeKey";
from q in SomeQuery select new SomeObject { 
    SomeKey = q.GetType().GetProperty("key").GetValue(q, null)
};

This fetches the value of a property known at runtime with reflection, but I find it hard to recommend code like this. Let's see why.

  1. First of all, it's not possible to dynamically define the name of the property in the anonymous type we are selecting (here, I have hardcoded it as SomeKey). Anonymous types may not have a name, but they are types like any other and in a language like C# this means that their members have to be known at compile time. So it would be theoretically impossible to create the anonymous type at runtime¹. Even if it were possible to do it, you could not access the properties on the anonymous type without, again, using reflection.

  2. It does not make much sense to "store the name of the information" as a property name (which is static) when you already have it in a variable (which is dynamic). If you want to pass a reference around, pass the contents of key.

  3. If you want to associate string keys with values it makes sense to use a dynamic structure as your backing store. For example, if SomeQuery is IEnumerable<IDictionary<string, object>> then you could simply do SomeKey = q[key]. If not, then perhaps it should have been?

  4. If for some reason you need all this dynamism, then a reasonable first approach would be to look into using ExpandoObject.

Upvotes: 3

Magnus
Magnus

Reputation: 46919

from q in SomeQuery select 
new SomeObject { key = q.GetType().GetProperty(key).GetValue(q) }

Upvotes: 2

Related Questions