Учитывая этот класс
public class Foo
{
public string Name { get; set; }
}
Этот метод (в некотором другом классе)...
private Func<Foo, string> Compile(string body)
{
ParameterExpression prm = Expression.Parameter(typeof(Foo), "foo");
LambdaExpression exp = DynamicExpressionParser.ParseLambda(new[] { prm }, typeof(string), body);
return (Func<Foo, string>)exp.Compile();
}
Возьмите правую часть выражения лямбда и верните мне делегата. Поэтому, если он называется так:
Foo f = new Foo { Name = "Hamilton Academicals" };
//foo => foo.Name.Substring(0,3)
Func<Foo, string> fn = Compile("foo.Name.Substring(0,3)");
string sub = fn(f);
Тогда sub будет иметь значение "Ham".
Все хорошо и хорошо, однако, я хотел бы создать подкласс Doo DynamicObject (так что я могу реализовать TryGetMember для динамической разработки значений свойств), поэтому я хочу взять выражение и получить эквивалент этого
Func<dynamic, dynamic> fn = foo => foo.Name.Substring(0,3);
Я пробовал Expression.Dynamic с помощью настраиваемого CallSiteBinder, но с ошибкой нет свойства или поля "Бар" существует в типе "Объект" (когда я пытаюсь получить доступ к foo.Bar динамически). Я предполагаю, что это потому, что вызов для получения foo.Bar должен быть динамически отправлен (с использованием Expression.Dynamic), но это не будет работать для меня, потому что ключевой целью является то, что пользователь может ввести простое выражение и выполнить его. Возможно ли?