Tag: 表达式 树

有效地消除.NET表达式树中的常见子表达式

我编写了一个DSL和一个从中生成.NET表达式树的编译器。 树中的所有表达式都是无副作用的,并且表达式保证是“非语句”表达式(没有本地,循环,块等)。 ( 编辑 :树可能包括文字,属性访问,标准操作符和函数调用 – 这可能正在做内容中的memoization等奇特的事情,但是外部无副作用)。 现在我想对它执行“Common sub-expression elimination”优化。 例如,给定一个对应于C#lambda的树: foo => (foo.Bar * 5 + foo.Baz * 2 > 7) || (foo.Bar * 5 + foo.Baz * 2 < 3) || (foo.Bar * 5 + 3 == foo.Xyz) …我想生成树等价的(忽略一些短路语义被忽略的事实): foo => { var local1 = foo.Bar * 5; // Notice that this local […]

为什么从表达式<Func >创建的Func 比直接声明的Func 慢?

为什么通过.Compile()从Expression<Func>创建的Func比使用直接声明的Func慢得多? 我刚刚使用Func直接声明为在我正在处理的应用程序中使用Expression<Func>创建的Expression<Func> ,我注意到性能下降了。 我刚做了一点测试,从Expression创建的Func占用了Func直接声明的时间的“几乎”。 在我的机器上,Direct Func大约需要7.5秒,而Expression<Func>大约需要12.6秒。 这是我使用的测试代码(运行Net 4.0) // Direct Func test1 = x => new Foo(x * 2); int counter1 = 0; Stopwatch s1 = new Stopwatch(); s1.Start(); for (int i = 0; i < 300000000; i++) { counter1 += test1(i).Value; } s1.Stop(); var result1 = s1.Elapsed; // Expression . Compile() Expression<Func> expression = […]

从Expression <Func >实例获取实际返回类型

我有一个接受Expression<Func>实例的方法。 我想得到特定表达式实例返回的实际数据类型,而不是object 。 我可以让它用于直接属性引用,所以如果我传入表达式x => x.IntegerProperty我可以得到一个整数的Type引用。 此方法需要将其转换为MemberExpression。 但是,我不能让它为任意表达式工作。 例如,如果表达式是x => x.IntegerProperty.ToString()我想获得字符串的Type引用。 我无法将其编译为MemberExpression,如果我只是.Compile()它并检查返回类型我得到“对象”。 如何查看特定的表达式实例并派生实际的返回类型?

如何结合两个lambdas

可能重复: 在c#中组合两个lamba表达式 我有两个以下表达式: Expression<Func> expr1 = s => s.Length == 5; Expression<Func> expr2 = s => s == “someString”; 现在我需要将它们与OR结合起来。 像这样的东西: Expression.Or(expr1, expr2) 有没有办法让这类似于上面的代码方式: expr1 || expr2 我理解在这个例子中我可以把它组合起来: Expression<Func> expr = s => s.Length == 5 || s == “someString” 但我不能在我的实际代码中这样做,因为我将expr1和expr2作为方法的参数。