gpt4 book ai didi

c# - 有人可以解释这个 C# lambda 语法吗?

转载 作者:可可西里 更新时间:2023-11-01 09:00:43 24 4
gpt4 key购买 nike

我最近发现一个静态方法声明为:

public class Foo
{
public static Func<HtmlHelper, PropertyViewModel, string> Render = (a, b) =>
{
a.RenderPartial(b);
return "";
};
}

Intellisense 建议用法是(例如):

string s = Foo.Render(htmlHelper, propertyViewModel);

那么下面的内容似乎是等价的:

public static string Render(HtmlHelper a, PropertyViewModel b)
{
a.RenderPartial(b);
return "";
}

A) 第一个样式的名称是什么?我意识到它正在使用 lambda;是 = 标志让我绊倒了。我无法将其标记化 ;)

B) 如果两个代码块是等价的,使用前者比使用后者有什么好处?

最佳答案

好的,为了清楚起见,我将再次写出这两个(并稍微修改方法以使其更短)

public static Func<HtmlHelper, PropertyViewModel, string> RenderDelegate = (a, b) =>
{
return a.RenderPartial(b);
};

public static string RenderMethod(HtmlHelper a, PropertyViewModel b)
{
return a.RenderPartial(b);
}

首先注意RenderDelegate是(如 S. DePouw 所写),只是使用 lambda 语法编写以下内容的一种奇特方式:

public static Func<HtmlHelper, PropertyViewModel, string> RenderDelegate = 
delegate(HtmlHelper a, PropertyViewModel b)
{
return a.RenderPartial(b);
};

RenderMethod之间的区别和 RenderDelegate是那个RenderMethod是一种方法,wheras RenderDelegate是委托(delegate),或者更具体地说,是委托(delegate)类型的字段。这意味着可以将 RenderDelegate 分配给。

什么是委托(delegate)?

委托(delegate)是一种类型。来自MSDN documentation :

A delegate is a type that defines a method signature, and can be associated with any method with a compatible signature.

本质上,您可以将委托(delegate)视为对方法的引用/指针,但是委托(delegate)指向的方法必须与委托(delegate)所期望的签名相匹配。所以例如 Func<HtmlHelper, PropertyViewModel, string>是一个委托(delegate),期望方法带有签名 string MyMethod(HtmlHelper, PropertyViewModel)因此我们可以像这样将具有该签名的方法分配给该委托(delegate):

RenderDelegate = RenderMethod;

重要的是要注意 Delegate 类型(注意大写 D)和 delegate 关键字(小写 d)之间的区别。在您的示例中,您使用 Func<>通用对象来压缩您的代码,但是它有点模糊这里真正发生的事情。 Func<HtmlHelper, PropertyViewModel, string>是一种继承自 Delegate 的类型,并且您可以使用 delegate 关键字来处理等效类型:

delegate string MyFunction<HtmlHelper helper, PropertyViewModel string>;
static MyFunction RenderDelegate = RenderMethod;

匿名方法

当我们在第一个示例中分配 RenderDelegate 时,我们没有将 RenderDelegate 设置为现有的命名方法,而是声明了一个内联的新方法。这被称为匿名方法并且有效,因为我们能够将代码块(也使用 delegate 关键字声明)作为委托(delegate)参数传递:

Lambda 函数

回到原来的语法 - 您的示例使用 lambda 语法以一种有趣的方式对匿名委托(delegate)进行 delcare。 Lambda 表达式是声明短内联方法的好方法,这些方法通常在处理列表时使用,例如假设我们想按名称对 HtmlHelper 对象列表进行排序。这样做的方法是将比较两个 HtmlHelper 对象的委托(delegate)传递给列表的排序方法,然后排序方法使用该委托(delegate)对列表中的元素进行比较和排序:

static int MyComparison(HtmlHelper x, HtmlHelper y)
{
return x.Name.CompareTo(y.Name);
}

static void Main()
{
List<HtmlHelper> myList = GetList();
myList.Sort(MyComparison);
}

为了避免散布大量的短方法,您可以使用匿名方法来在线删除排序方法。这一点真正有用的是,内联方法可以访问在包含范围内声明的变量:

int myInt = 12;
List<HtmlHelper> myList = GetList();
myList.Sort(
delegate (HtmlHelper x, HtmlHelper y)
{
return x.Name.CompareTo(y.Name) - myInt;
});

然而,这仍然是相当多的输入,所以 lambda sytax 诞生了,现在你可以这样做:

List<HtmlHelper> myList = GetList();
myList.Sort((x, y) => {return x.Name.CompareTo(y.Name)});

然而,以这种方式声明“正常”方法对我来说似乎完全没有意义(并且让我的眼睛流血)

委托(delegate)难以置信有用,并且(除其他外)是 .Net 事件系统的基石。一些更多的阅读来清理一下:

关于c# - 有人可以解释这个 C# lambda 语法吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2113779/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com