I recently came upon a static method declared as:
public class Foo
{
public static Func<HtmlHelper, PropertyViewModel, string> Render = (a, b) =>
{
a.RenderPartial(b);
return "";
};
}
Intellisense suggests the usage is (for example):
string s = Foo.Render(htmlHelper, propertyViewModel);
It would seem then that the following is equivalent:
public static string Render(HtmlHelper a, PropertyViewModel b)
{
a.RenderPartial(b);
return "";
}
A) What is the name of the first style? I realize it's using lambdas; it's the =
sign that is tripping me up. I can't tokenize it 😉
B) If the two code blocks are equivalent, what is the benefit of using the former over the latter?
Best Answer
Ok, for clarity I'm going to write the two out again (and slightly modify the method to make it shorter)
Firstly note that
RenderDelegate
is (as S. DePouw writes), just a fancy way of using lambda syntax to write the following:The difference between
RenderMethod
andRenderDelegate
is thatRenderMethod
is a method, wherasRenderDelegate
is a delegate, or more specifically a field of type Delegate. This means that RenderDelegate can be assigned to.What is a Delegate?
A delegate is a type. From the MSDN documentation:
Essentially you can think of a delegate as a reference / pointer to a method, however the method that the delegate points to has to match the signature that the delegate is expecting. So for example
Func<HtmlHelper, PropertyViewModel, string>
is a Delegate that expects methods with the signaturestring MyMethod(HtmlHelper, PropertyViewModel)
and so we are able to assign methods with that signature to that delegate like this:Its important to note the difference between the Delegate type (note the capital D) and the delegate keyword (lower case d). In your example your using the
Func<>
generic object to condense your code, however its kind of obscuring whats really going on here.Func<HtmlHelper, PropertyViewModel, string>
is a type which inherits fromDelegate
, and you could use the delegate keyword to delcare an equivalent type:Anonymous methods
When we assigned RenderDelegate in the first example, we didnt set RenderDelegate to an existing named method, instead we declared a new method in-line. This is known as an Anonymous Method and works because we are able to pass a code block (also declared using the delegate keyword) as a delegate parameter:
Lambda functions
Back to the original syntax - your example is using lambda syntax to delcare an anonymous delegate in a funny way. Lambda expressions are good way of declaring short inline methods which might commonly be used when dealing with lists, for example supposing we want to sort a list of HtmlHelper objects by their Name. The way of doing this is to pass a Delegate that compares two HtmlHelper objects to the lists Sort method, the sort method then uses that delegate to compare and sort the elements in the list:
To avoid having loads of short methods scattered around, you can use anonymous methods to delcare the sorting method in-line. Whats also really useful about this is that the in-line method has access to variables declared in the containing scope:
Thats still fairly quite a lot of typing however, and so the lambda sytax was born and now you can do this instead:
Declaring "normal" methods in this way however seems to be completely pointless to me (and makes my eyes bleed)
Delegates are incredibly useful and are (among other things) the cornerstone of the .Net event system. Some more reading to clear things up a bit: