随着lambda表达式(内联代码)等新功能的出现,这是否意味着我们不必再使用委托或匿名方法?在我看到的几乎所有样本中,都是使用新语法重写的。有没有一种情况下,委托语法优于匿名方法的lambda表达式?
任何我们仍然必须使用委托和lambda表达式的地方都不行?
随着lambda表达式(内联代码)等新功能的出现,这是否意味着我们不必再使用委托或匿名方法?在我看到的几乎所有样本中,都是使用新语法重写的。有没有一种情况下,委托语法优于匿名方法的lambda表达式?
任何我们仍然必须使用委托和lambda表达式的地方都不行?
lambda是匿名委托的快捷方式,但您将始终使用委托。委托指定方法签名。你可以这样做:
delegate(int i) { Console.WriteLine(i.ToString()) }
可以
f => Console.WriteLine(f.ToString())
Lambda表达式替换只是“语法糖”,编译器将产生相应的代表为您服务。你可以使用Lutz Roeder的Reflector来调查。
实际上,lambda表达式比语法糖多一点,因为它们可以编译到表达式树中并进行操作。 – 2008-09-19 23:24:35
反射器现在由redgate拥有[http://www.red-gate.com/products/reflector/] – cori 2008-09-20 02:40:47
的Lamda的是代表只是语法糖,他们不只是为inline,可以做到以下几点:
s.Find(a =>
{
if (a.StartsWith("H"))
return a.Equals("HI");
else
return !a.Equals("FOO");
});
并定义事件时,或代表仍在使用,当你有很多的争论,并希望实际上强烈键入正在调用的方法。
是的,有些地方直接使用匿名代理和lambda表达式不起作用。
如果一个方法需要一个无类型的Delegate,那么编译器不知道该如何解析匿名委托/ lambda表达式,并且会得到编译器错误。
public static void Invoke(Delegate d)
{
d.DynamicInvoke();
}
static void Main(string[] args)
{
// fails
Invoke(() => Console.WriteLine("Test"));
// works
Invoke(new Action(() => Console.WriteLine("Test")));
Console.ReadKey();
}
的代码失败的行会得到编译器错误“无法转换lambda表达式键入‘System.Delegate’,因为它不是一个委托类型”。
我认为提问者询问`delegate`关键字已过时,以支持更新的基于lambda的语法。她将“匿名方法和代表”组合在一起。 – nawfal 2013-12-20 10:02:44
委托在C#中有两个含义。
关键字delegate
可用于定义函数签名类型。这通常用于确定高阶函数的签名,即将其他函数作为参数的函数。委托的这种使用仍然相关。
关键字delegate
也可用于定义内联匿名函数。在函数只是单个表达式的情况下,lambda语法是一个更简单的选择。
Lambda表达式不是(也不是意味着)将取代(隐藏)代表的银色子弹。它与当地的小东西是伟大的,如:
List<string> names = GetNames();
names.ForEach(Console.WriteLine);
在另一方面,它是非常简单的滥用它们。长和/或复杂的lambda表达式都趋向于:
少对象,因此“它意味着我们不'不必再使用委托或匿名方法了吗?“否 - 使用Lambda表达式来赢得时间/可读性,否则请考虑使用委托。
哇!我从来没有想过这个!有没有办法做谓词,即names.Where(!string.IsNullOrEmpty)); ?我试过了,它不适合我。 哎呀!如果我删除!操作数它工作,为什么?我甚至试图把它放在括号里,但它不能完全调用它,有没有办法? 我们实际上正试图将string.IsNullOrEmpty转换为string.IsNotNullOrEmpty ... – Shimmy 2009-07-23 04:53:56
其中一个没有那么大较旧的delegate
语法的优点是如果您不在方法体中使用它,则不需要指定参数。从msdn
有一种情况,其中一个匿名方法提供的功能 在lambda表达式未找到。匿名方法使您可以省略参数列表 。这意味着匿名方法可以将 转换为具有各种签名的委托。对于lambda表达式,这不是 。
例如,你可以这样做:
Action<int> a = delegate { }; //takes 1 argument, but not specified on the RHS
虽然失败:
button.onClicked += delegate { Console.WriteLine("clicked"); };
:
Action<int> a = => { }; //omitted parameter, doesnt compile.
这种技术撰写事件处理程序时,像大多来得心应手这不是强的优势。最好采用总是imho的新语法。
另请参见[差异之间的差异 - 匿名方法和lambda表达式](http://stackoverflow.com/questions/208381/whats-the-difference-between-anonymous-methods-c -2-0和lambda表达式)的一般差异。 – nawfal 2014-07-03 11:30:07