Dynamic 动态构建lambda表达式
我知道如何构建一个简单的lambda,比如x=>x>5:Dynamic 动态构建lambda表达式,dynamic,lambda,tree,expression,expression-trees,Dynamic,Lambda,Tree,Expression,Expression Trees,我知道如何构建一个简单的lambda,比如x=>x>5: int[] nbs = new[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 }; IEnumerable<int> result1 = nbs.Where(x => x > 5); ParameterExpression parameter = Expression.Parameter(typeof(int), "x"); ConstantExpression co
int[] nbs = new[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
IEnumerable<int> result1 = nbs.Where(x => x > 5);
ParameterExpression parameter = Expression.Parameter(typeof(int), "x");
ConstantExpression constant = Expression.Constant(5);
BinaryExpression expressionBody = Expression.GreaterThan(parameter, constant);
Expression<Func<int, bool>> expression = Expression.Lambda<Func<int, bool>>(expressionBody, parameter);
IEnumerable<int> result2 = nbs.Where(expression.Compile());
但是,如果能够动态地构造复杂的lambda,我仍然感兴趣 这段代码完成了这项工作
ParameterExpression parameter = Expression.Parameter(typeof(Person), "p");
ConstantExpression my_null_object = Expression.Constant(null);
ConstantExpression gender = Expression.Constant("Gender");
MethodCallExpression methodcall = Expression.Call(parameter, typeof(Person).GetMethod("FindAttribute"), gender);
BinaryExpression is_null = Expression.Equal(methodcall, my_null_object);
ConstantExpression constant = Expression.Constant("Female");
MemberExpression member = Expression.Property(methodcall, typeof(Attribute).GetProperty("Value"));
BinaryExpression expressionBody = Expression.Equal(member, constant);
BinaryExpression cond = Expression.AndAlso(Expression.IsFalse(is_null), expressionBody);
这样可能更清楚
ParameterExpression parameter = Expression.Parameter(typeof(Person), "p");
ConstantExpression my_null_object = Expression.Constant(null);
MethodCallExpression methodcall = Expression.Call(parameter, typeof(Person).GetMethod("FindAttribute"), Expression.Constant("Gender"));
BinaryExpression cond = Expression.AndAlso(
Expression.IsFalse(Expression.Equal(methodcall, my_null_object)),
Expression.Equal(
Expression.Property(methodcall, typeof(Attribute).GetProperty("Value")),
Expression.Constant("Female")
)
);
空条件运算符是一种语言功能。可以将其转换为以下代码:
var attribute = p.FindAttribute("Gender");
return attribute == null ? false : attribute.Value == "Female";
要构建表达式树,可以使用expression.Block
:
var p = Expression.Parameter(typeof(Person), "p");
var findAttribute = Expression.Call(p,
typeof(Person).GetMethod(nameof(Person.FindAttribute)),
Expression.Constant("Gender"));
var attribute = Expression.Parameter(typeof(Attribute), "attribute");
var body = Expression.Block(
new[] {attribute}, // local variables
new Expression[]
{
Expression.Assign(attribute, findAttribute),
Expression.Condition(
Expression.Equal(attribute, Expression.Constant(null)),
Expression.Constant(false),
Expression.Equal(
Expression.PropertyOrField(attribute, "Value"),
Expression.Constant("Female")))
}
);
var lambda = Expression.Lambda<Func<Person, bool>>(body, p);
var p=Expression.Parameter(typeof(Person),“p”);
var findAttribute=Expression.Call(p,
typeof(Person).GetMethod(nameof(Person.FindAttribute)),
表达式。常数(“性别”);
var attribute=Expression.Parameter(typeof(attribute),“attribute”);
var body=Expression.Block(
新[]{attribute},//局部变量
新表达式[]
{
Expression.Assign(属性,findAttribute),
表达式.条件(
Expression.Equal(属性,Expression.Constant(null)),
表达式。常量(false),
表达式。相等(
Expression.PropertyOrField(属性,“值”),
表达式。常量(“女性”))
}
);
var lambda=表达式lambda(body,p);
var attribute = p.FindAttribute("Gender");
return attribute == null ? false : attribute.Value == "Female";
var p = Expression.Parameter(typeof(Person), "p");
var findAttribute = Expression.Call(p,
typeof(Person).GetMethod(nameof(Person.FindAttribute)),
Expression.Constant("Gender"));
var attribute = Expression.Parameter(typeof(Attribute), "attribute");
var body = Expression.Block(
new[] {attribute}, // local variables
new Expression[]
{
Expression.Assign(attribute, findAttribute),
Expression.Condition(
Expression.Equal(attribute, Expression.Constant(null)),
Expression.Constant(false),
Expression.Equal(
Expression.PropertyOrField(attribute, "Value"),
Expression.Constant("Female")))
}
);
var lambda = Expression.Lambda<Func<Person, bool>>(body, p);