如何创建一个表达式,该表达式抛出exception或根据条件返回值?
我正在努力构建一个表达式,如果条件为true则抛出一个exception,如果它是false,它应该返回一个值,但我总是得到ArgumentException
:
var expr = Expression.Condition( Expression.Equal(Expression.Constant(0), Expression.Constant(0)), Expression.Throw(Expression.Constant(new DivideByZeroException())), Expression.Constant(1)); var lambda = Expression.Lambda<Func>(expr); var result = lambda.Compile()();
如果我将Expression.Empty()
作为Condition
的第三个参数然后运行,但如果条件为false,则不会得到所需的结果。
这样做。
var expr = Expression.Block( Expression.IfThen( Expression.Equal(Expression.Constant(1), Expression.Constant(1)), Expression.Throw( Expression.New(typeof(DivideByZeroException)) ) ), Expression.Constant(1) ); var lambda = Expression.Lambda>(expr); var result = lambda.Compile()();
Conditional
更类似于三元运算符。 所以你写的更像是在C#中:
return (0 == 0) ? throw new DivideByZeroException() : 1;
我将常量exception更改为动态创建的exception,我假设这是首选。
条件表达式必须从每个分支返回相同的类型。 你正在尝试的是等同于
var x = 0==0 ? throw new DivideByZeroException() : 1;
这是无效的。 您可能只会导致 DivideByZeroException
:
var expr = Expression.Condition( Expression.Equal(Expression.Constant(0), Expression.Constant(0)), Expression.Divide(Expression.Constant(1), Expression.Constant(0)), Expression.Constant(1));
只需创建一个为您抛出exception的方法,并具有您想要的任何类型:
public static T ThrowHelper(Exception e) { throw e; }
然后创建一个调用该方法的表达式。 这使得表达式抛出表达式而不是语句,并允许该表达式具有您想要的任何类型:
var throwMethod = typeof(TheClassThrowIsIn) .GetMethod("ThrowHelper", BindingFlags.Static) .MakeGenericMethod(typeof(int)); var expr = Expression.Condition( Expression.Equal(Expression.Constant(0), Expression.Constant(0)), Expression.Call(throwMethod, Expression.Constant(new DivideByZeroException())), Expression.Constant(1));