属性select器expression式<Func <T >>。 如何获取/设置选定的属性值

我有一个目标,我想以这样的方式来构build:

var foo = new FancyObject(customer, c=>c.Email); //customer has Email property 

我应该如何声明第二个参数?

如何访问选定属性setter / getter的代码将如何?

UPD。 该模型中有几个实体具有Email属性。 所以可能签名会看起来像:

 public FancyObject(Entity holder, Expression<Func<T>> selector) 

和构造函数调用

 var foo = new FancyObject(customer, ()=>customer.Email); 

该参数将是一个Expression<Func<Customer,string>> selector 。 读它可以通过平面编译:

  Func<Customer,string> func = selector.Compile(); 

那么你可以访问func(customer) 。 指派更棘手。 对于简单的select器,你可以希望你可以简单地分解为:

 var prop = (PropertyInfo)((MemberExpression)selector.Body).Member; prop.SetValue(customer, newValue, null); 

但是更复杂的expression式可能需要手动树遍历,或者一些4.0expression式节点types:

  Expression<Func<Customer, string>> email = cust => cust.Email; var newValue = Expression.Parameter(email.Body.Type); var assign = Expression.Lambda<Action<Customer, string>>( Expression.Assign(email.Body, newValue), email.Parameters[0], newValue); var getter = email.Compile(); var setter = assign.Compile(); 

它看起来像这个types必须具有两个types参数 – 源代码和结果。 例如,您可以使用:

 var foo = new FancyObject<Customer, string>(customer, c => c.Email); 

第一个参数是TSourcetypes,第二个参数是Expression<Func<TSource, TResult>>

 public class FancyObject<TSource, TResult> { private readonly TSource value; private readonly Expression<Func<TSource, TResult>> projection; public FancyObject(TSource value, Expression<Func<TSource, TResult>> projection) { this.value = value; this.projection = projection; } } 

您可以使这个更简单的使用非genericstypes的静态方法:

 var foo = FancyObject.Create(customer, c => c.Email); 

这可以使用types推断来计算types参数。