博客园  :: 首页  :: 联系 :: 管理

C#匿名方法

Posted on 2007-07-15 20:13  sunrack  阅读(443)  评论(0编辑  收藏  举报

在C# 1.1里,声明和使用委托要求你有委托和一个在委托被触发时具有匹配签名的能够执行的方法,以及一个将命名方法与委托关联的分配语句。作为C# 2.0的新特性,匿名方法基本上能够提供与先前命名方法相同的功能,但是它已经不再需要一个在关联到委托之前就明确创建的方法了。

你可以把匿名方法想象为一个实现与委托进行关联这项功能的便捷途径。如果同时看一下匿名方法实现和命名方法实现所取得IL结果,你会发现这两者之间的差别非常小。当编译器碰到匿名方法的时候,它会在类里面创建一个命名方法,并将它与委托进行关联。所以匿名方法在运行期间与命名方法的性能非常类似——性能的增加体现在开发人员的生产效率上,而不是运行期间的执行上。

如何使用匿名方法

多用代码少用说教来解释和理解匿名方法会容易一些。下面的例子应该能够说明你自己可以如何利用匿名方法的优势:

例1——基础知识

使用匿名方法很简单。你只需要把匿名方法放在你通常放命名方法的关联语句里。在下面这个例子里,我把匿名方法和示例1的委托关联在一起:

示例列表1

#region Simple example - Example1
privatedelegatevoidExample1();

privatevoid btnExample1_Click(object sender, EventArgs e)
{
//Declare an instance of the Example1 delegate.
// You can see where I''m using the anonymous
// method in place of a named method - it follows
// the delegate() keyword.
Example1 example =
newExample1(
delegate()
{
MessageBox.Show("Example1");
});

example();
}
#endregion

例2——变量范围

任何在匿名方法里声明的变量的范围都不会超出匿名方法的代码块。但是,匿名方法确实具有访问它们代码块之外的变量的能力,只要这些变量在匿名方法所使用的范围里。这些变量被微软称为外部变量。下面示2显示了匿名方法如何引用外部变量:

示例列表2

#region Variable scope example - Example2
privatedelegatevoidExample2();

privatevoid btnExample2_Click(object sender, EventArgs e)
{
//Setup our parameters.
string firstName = "Zach";
string lastName = "Smith";

//Create an instance of the Example2 delegate with an
// anonymous method.
Example2 example =
newExample2(
delegate() {
MessageBox.Show(firstName + " " + lastName);
});

//Execute the delegate.
example();
}
#endregion

要注意的是,根据MSDN的文档,匿名方法里的refout参数无法被访问到。

例3——参数的传递

你可以将参数传递给匿名方法,方式就和你处理引用命名方法参数的委托一样。下面的示例3说明这种类型的功能:

示例列表3

#region Parameter example - Example3
privatedelegatevoidExample3(string firstName, string lastName);

privatevoid btnExample3_Click(object sender, EventArgs e)
{
//Setup our parameters.
string parameter1 = "Zach";
string parameter2 = "Smith";

//Create an instance of the Example3 delegate with an
// anonymous method.
Example3 example =
newExample3(
delegate(string firstName, string lastName)
{
MessageBox.Show("Example3: " + firstName + " " + lastName);
});

//Execute the delegate.
example(parameter1, parameter2);
}
#endregion