Преобразовать выражение Linq «obj => obj.Prop» в «parent => parent.obj.Prop»
У меня есть существующее выражение типаExpression<Func<T, object>>
; он содержит такие значения, какcust => cust.Name
.
У меня также есть родительский класс с полем типаT
, Мне нужен метод, который принимает выше в качестве параметра и генерирует новое выражение, которое принимает родительский класс (TModel
) в качестве параметра. Это будет использоваться как параметр выражения метода MVC.
Таким образом,cust => cust.Name
становитсяparent => parent.Customer.Name
.
Точно так же,cust => cust.Address.State
становитсяparent => parent.Customer.Address.State
.
Вот моя первоначальная версия:
//note: the FieldDefinition object contains the first expression
//described above, plus the MemberInfo object for the property/field
//in question
public Expression<Func<TModel, object>> ExpressionFromField<TModel>(FieldDefinition<T> field)
where TModel: BaseModel<T>
{
var param = Expression.Parameter(typeof(TModel), "t");
//Note in the next line "nameof(SelectedItem)". This is a reference
//to the property in TModel that contains the instance from which
//to retrieve the value. It is unqualified because this method
//resides within TModel.
var body = Expression.PropertyOrField(param, nameof(SelectedItem));
var member = Expression.MakeMemberAccess(body, field.Member);
return Expression.Lambda<Func<TModel, object>>(member, param);
}
В настоящее время я получаю сообщение об ошибке, когда у меня есть поле с несколькими частями (т.е.cust.Address.State
вместо простоcust.Name
). Я получаю ошибку наvar member
строка о том, что указанный член не существует - это правда, так как тело в этом относится к дочернему элементу родителя (Customer
), а не элемент, который содержит член (Address
).
Вот что я хотел бы сделать:
public Expression<Func<TModel, object>> ExpressionFromField<TModel>(FieldDefinition<T> field)
where TModel: BaseModel<T>
{
var param = Expression.Parameter(typeof(TModel), "t");
var body = Expression.PropertyOrField(param, nameof(SelectedItem));
var IWantThis = Expression.ApplyExpressionToField(field.Expression, body);
return Expression.Lambda<Func<TModel, object>>(IWantThis, param);
}
Любая помощь в достижении этой точки будет принята с благодарностью.
Изменить: это было отмечено как возможный дубликатэтот вопрос; однако единственное реальное сходство - это решение (которое на самом деле одно и то же). Составление выражений не является интуитивно понятным решением для доступа к вложенным свойствам с помощью выражений (если ваша интуиция не руководствуется определенным опытом, который не следует предполагать). Я также отредактировал вопрос, чтобы отметить, что решение должно быть подходящим для параметра метода MVC, который ограничивает возможные решения.