在表达式树中实现 Not,.net 4
Posted
技术标签:
【中文标题】在表达式树中实现 Not,.net 4【英文标题】:Implement Not in expression trees, .net 4 【发布时间】:2011-01-11 00:35:53 【问题描述】:是否可以实现! (不)使用表达式树。我有兴趣创建一个 C# eval 类,它将解析和评估包含 true、false、||、&& 和 ! 的逻辑表达式。我知道 && 和 ||目前由 .NET 4 表达式树支持,但我想知道它们是否是一种实现 summat 的方法,例如 !(x && y) || z 其中 z=false,y=true 和 z=false。
目前我正在使用基于标准堆栈的标记器、解析器、评估器来评估这些类型的表达式,但如果可以动态创建和执行合适的表达式树,我很乐意将其转储。
【问题讨论】:
标题说 .NET 4 但标签说 .NET 3.5。哪一个? 3.5 当我上次检查时,它没有实现,但它现在在文档中,所以忽略 .net 条目。 【参考方案1】:我通常发现值得编写一个 lambda 表达式来执行我想要的操作,然后查看 C# 编译器如何处理它。
所以这段代码:
Expression<Func<bool,bool>> func = x => !x;
被编译成:
ParameterExpression expression2;
Expression<Func<bool, bool>> expression =
Expression.Lambda<Func<bool, bool>>(Expression.Not(
expression2 = Expression.Parameter(typeof(bool), "x")),
new ParameterExpression[] expression2 );
(为格式化道歉 - 很难知道如何处理。)
这是使用 Reflector 反编译的,但其“优化”设置为 .NET 2.0 以避免使用 lambda 语法。
一旦您通过了垃圾邮件,您就会看到它正在使用Expression.Not
。 && 使用 Expression.AndAlso
和 ||使用Expression.OrElse
。
【讨论】:
嗨乔恩,像往常一样,一个快速而出色的答案。鲍勃。 很棒的技术,可以更好地了解引擎盖下发生的事情。 我最初拥有完整的!(x && y) || z
,但它构建的代码太乱了:)【参考方案2】:
这已经存在于System.Linq.Expressions
中。见UnaryExpression。除非有一些你不喜欢的表达方式,否则我建议使用它们。还有一些方法可以从源代码创建抽象语法树,特别是在 Microsoft.Scripting.Ast
(在 DLR:Microsoft.Scripting 中找到)。
【讨论】:
【参考方案3】:这可能有用: http://community.bartdesmet.net/blogs/bart/archive/2009/08/10/expression-trees-take-two-introducing-system-linq-expressions-v4-0.aspx
【讨论】:
以上是关于在表达式树中实现 Not,.net 4的主要内容,如果未能解决你的问题,请参考以下文章
如何使用 asp.net Web 表单在 Telerik 树中实现搜索和过滤