代码改变世界

[翻译]Lambda表达式和表达式树(Lambda Expressions and Expression Trees)

2008-08-29 11:38  G yc {Son of VB.NET}  阅读(1473)  评论(1编辑  收藏  举报

        原文地址:http://blogs.msdn.com/vbteam/archive/2007/09/11/lambda-expressions-and-expression-trees.aspx

        作者: Tim

 

最近我的《Lambda 表达式的文章被发布到MSDN magazine上了。所以在这个帖子我将展开讨论之前文章中的想法(Ideas),如果这里想法使你感到迷茫,请你先去读一下之前的文章。 

 

Lambda 表达式 非常Cool ,除了文章中所描述的,Lambda表达式还可以捕获另一个可读形式的Lambda表达式的内容,并把它当作数据而不是可执行代码。

 
例如,下面几行代码将Lambda表达式转换成可调用委托(Callable delegate 

Dim f As Func(Of Integer, Integer) = function(x) x * 2

Dim r = f(10)

在这个实例中,第一行代码将建立一个Lambda 表达式并将它神奇的配额给一个可调用委托(Callable delegate f 。之后,第二行 调用 f 并返回 20.

 
这个非常酷,我希望我的文章能说明我为什么觉得的原因。还有更酷的你可以分配一个Lambda 表达式到一个特殊变量类型并且编译器将帮你做更多魔法般的事: 

Dim e As Expression(Of Func(Of Integer, Integer)) = function(x) x * 2

 
在这个代码示例中,e 不是可调用委托(Callable delegate)。实际上,它是一个表达式树。一个表达式树是Lambda表达式在数据表单中的表示形式,它可以方便你阅读和编写lambda表达式。 

 

如果你在调试器中查看e的值,你将会看到 你可以简单的推测那个表达式是一个整数变量x乘以常数2 

 

默认的,IEnumerable 的扩展查询操作使用Lambda表达式。IQueryable的扩展查询使用表达式树。因此,当你在queryable对象上使用查询时,编译器将产生表达式树通过Lambda表达式树。 

 

Scott,我们小组开发人员之一。他写了一篇极好的文章来说明这些想法。他有一个很好的实例来展示使用若干Lambda表达式来表示表达式树。 

 
你可以用表达式树做什么? 
 
通常,你可以做2件事: 
  1. 表达式树中的数据,自定义处理。你也可以转换表达式树中的数据到另一个格式(像是XML 
  2. 使用.Compile() 方法将表达式树变成一个可执行的委托 
  3. 使用动态条件构建查询:查看Jonathan's (我们的 PM)发布的文章。他有一个很好的实例来说明你如何操作表达式树和Lambda表达式来构建自定义条件。 

 

第二项是有趣的,因为它意味着 你可以写一个Lambda表达式到表达式树中或者类似的等待,并返回一个可调用委托(Callable delegate)。 

Dim e As Expression(Of Func(Of Integer, Integer)) = function(x) x * 2

Dim f = e.Compile

Dim r = f(10)

 
在这个示例中,r的值是20,就像先前例子一样我们直接分配了Lambda到一个委托(类)。 
 
为什么有趣? 
 

除了表达式树,不可能用描述(格式)来描述表达式。除非使用IL(中间语言),但那个太低级来来重新建立用户需要的表达式。相比之下,表达式树提供了一个高级的 树的形式来表示一个表达式,所以你可以简单的理解用户表达式的目的。 

 
这有可能使你感兴趣的使用表达式树: 

 

  1. 表达式,可以转换他们成为委托并调用它们。  
  2. 转换表达式到SQL,那将使得它们可被服务器执行(这就是LINQ to SQL 做的)  
  3. 转换表达式到XML并写入它们到磁盘上。  
  4. 转换表达式到自定义格式,可以通过网络协议放松到服务器,并可以重新建立表达式树,之后根据它执行与/或(And/OR)。