Lambda Expressions (C # Programming Guide)

Source: Internet
Author: User

This is a document published by Microsoft in Visual Studio 2015 that is not remembered.

Lambda Expressions (C # Programming Guide)

Visual Studio 2015

A LAMBDA expression is an anonymous function that can be used to create a delegate [U1] or an expression tree type [U2]. By using a lambda expression, you can write a local function that can be passed as a parameter or returned as a function call value. Lambda expressions are particularly useful for writing LINQ query expressions.

To create a lambda expression, you specify an input parameter (if any) on the left side of the lambda operator =>[u3], and then enter an expression or a block of statements on the other side. For example, the lambda expression x = = X * x refers to the parameter named X and returns the square value of x. As the following example shows, you can assign this expression to a delegate type:

C#

delegate int del (int i);

static void Main (string[] args)

{

Del mydelegate = x + x * x;

Int J = MyDelegate (5); j = 25

}

To create an expression tree type:

C#

Using System.Linq.Expressions;

Namespace ConsoleApplication1

{

Class Program

{

static void Main (string[] args)

{

Expression<del> Myet = x = x * x;

}

}

}

the = = operator has the same precedence as the assignment operator (=) and is a right-associative operation (see the "Binding" section of the "operator" article).

LAMBDA is used as a parameter to a standard query operator method (such as Where) in a method-based LINQ query.

When you invoke the Where method in the Enumerable class using method-based syntax (as in LINQ to Objects and LINQ to XML), the parameter is the delegate type System.func<t, tresult>. It is most convenient to create this delegate using a LAMBDA expression. For example, when you call the same method in the System.Linq.Queryable class (as in Linq to SQL), the parameter type is SYSTEM.LINQ.EXPRESSIONS.EXPRESSION<FUNC> Func is any one Func delegate with a maximum of 16 input parameters. Similarly, a LAMBDA expression is just a very concise way to construct the expression tree. Although the objects created by lambda actually have different types, lambda makes the Where call look similar.

In the previous example, notice that the delegate signature has an implicit type input parameter of type int and returns an int. You can convert a LAMBDA expression to a delegate of that type, because the expression also has an input parameter (x), and a compiler can implicitly convert to the return value of type int . (type inference is discussed in more detail in the following sections.) When the delegate is invoked using input parameter 5, it returns the result 25.

Lambda is not allowed on the left side of the IS or as operator.

All restrictions that apply to anonymous methods also apply to LAMBDA expressions. For more information, see Anonymous Methods (C # Programming Guide).

An expression lambda

The lambda expression that the expression is on the right side of the = = operator is called expression Lambda. Expression Lambda is widely used in the construction of Expression trees (C # and Visual Basic). The expression lambda returns the result of an expression and takes the following basic form:

(input parameters) = Expression

Parentheses are optional only if the lambda has only one input parameter, otherwise parentheses are required. Two or more input parameters in parentheses are delimited by commas:

C#

(x, y) = x = = Y

Sometimes, it is difficult or impossible for the compiler to infer the input type. If this occurs, you can explicitly specify the type as shown in the following example:

C#

(int x, string s) = s.length > x

Specify 0 input parameters with an empty parenthesis:

C#

() = SomeMethod ()

In the previous example, note that the body of an expression Lambda can contain a method call. However, if you want to create an expression tree that is evaluated outside the. NET Framework (for example, in SQL Server), you should not use a method call in a lambda expression. Outside of the. NET common language runtime context, methods will have no meaning.

Statement Lambda

A statement lambda is similar to an expression lambda expression, except that the statement is enclosed in curly braces:

(input parameters) = {statement;}

The body of a statement lambda can contain any number of statements, but in practice there are usually no more than two or three.

C#

delegate void Testdelegate (string s);

...

Testdelegate Mydel = n = {string s = n + "" + "world"; Console.WriteLine (s); };

Mydel ("Hello");

Like anonymous methods, statement lambda cannot be used to create an expression tree.

Asynchronous lambda

By using the async and await keywords, you can easily create lambda expressions and statements that contain asynchronous processing. For example, the following Windows forms sample contains an event handler that calls and waits for an async method Examplemethodasync.

C#

public partial class Form1:form

{

Public Form1 ()

{

InitializeComponent ();

}

Private async void Button1_Click (object sender, EventArgs e)

{

Examplemethodasync returns a Task.

await Examplemethodasync ();

TextBox1.Text + = "\r\ncontrol returned to click event Handler.\r\n";

}

Async Task Examplemethodasync ()

{

The following line simulates a task-returning asynchronous process.

Await Task.delay (1000);

}

}

You can use asynchronous lambda to add the same event handler. To add this handler, add an async modifier before the lambda parameter list, as shown in the following example.

C#

public partial class Form1:form

{

Public Form1 ()

{

InitializeComponent ();

Button1. Click + = Async (sender, e) = =

{

Examplemethodasync returns a Task.

await Examplemethodasync ();

TextBox1.Text + = "\r\ncontrol returned to click event Handler.\r\n";

};

}

Async Task Examplemethodasync ()

{

The following line simulates a task-returning asynchronous process.

Await Task.delay (1000);

}

}

For more information about how to create and use async methods, see asynchronous Programming with Async and Await (C # and Visual Basic).

Lambda with standard query operators

Many standard query operators have input parameters, and their type is one of the generic delegate series Func<t, Tresult>. These delegates use type parameters to define the number and type of input parameters, and the return type of the delegate. The Func delegate is useful for encapsulating user-defined expressions that apply to each element in a set of source data. For example, consider the following delegate types:

C#

Public delegate TResult func<targ0, tresult> (TArg0 arg0)

The delegate can be instantiated as func<int,bool> MyFunc, where int is the input parameter andbool is the return value. The return value is always specified in the last type parameter. func<int, string, bool> definition contains two input parameters (int and string) and returns a delegate of type bool . When the following Func delegate is called, the delegate returns TRUE or false to indicate whether the input parameter equals 5:

C#

Func<int, bool> myFunc = x = x = = 5;

BOOL result = MyFunc (4); Returns false of course

When the parameter type is expression<func> , you can also provide a LAMBDA expression, such as in a standard query operator defined within System.Linq.Queryable. If you specify the expression<func> parameter, the lambda is compiled into an expression tree.

A standard query operator is shown here, with the Count method:

C#

int[] numbers = {5, 4, 1, 3, 9, 8, 6, 7, 2, 0};

int oddnumbers = numbers. Count (n = = n% 2 = = 1);

The compiler can infer the type of the input parameter, or you can explicitly specify the type. This special lambda expression calculates the number of integers divided by 2 o'clock (n) with the remainder of 1.

The following line of code will generate a sequence that contains all the elements in the numbers array to the left of 9 because it is the first number in the sequence that does not meet the criteria:

C#

var firstNumbersLessThan6 = numbers. TakeWhile (n = n < 6);

This example shows how to specify multiple input parameters by enclosing the input parameters in parentheses. The method returns all elements in a numeric array until it encounters a number whose value is less than its position. Do not confuse the lambda operator (= =) with the greater than equals operator (>=).

C#

var firstsmallnumbers = numbers. TakeWhile ((n, index) = n >= index);

Type inference in Lambda

When you write a lambda, you typically do not have to specify a type for the input parameter, because the compiler can infer the type based on the lambda body, the delegate type of the parameter, and other factors described in the C # language specification. For most standard query operators, the first input is the element type in the source sequence. Therefore, if you are querying ienumerable<customer>, the input variable is inferred as a Customer object, which means that you can access its methods and properties:

C#

Customers. Where (c = = C.city = = "London");

The general rules for LAMBDA are as follows:

    • A LAMBDA must contain the same number of arguments as the delegate type.
    • Each input parameter in a LAMBDA must be implicitly convertible to its corresponding delegate parameter.
    • The return value of the LAMBDA, if any, must be implicitly convertible to the return type of the delegate.

Note that the lambda expression itself does not have a type, because the general type system does not have an internal concept of "lambda expression". However, it is sometimes convenient to talk about the "type" of a lambda expression in an informal way. In these cases, the type refers to the type of expression to which the delegate type or lambda expression is converted.

Scope of variables in a LAMBDA expression

Within a method that defines a lambda function or a type that contains a lambda expression, lambda can refer to an external variable within the scope (see Anonymous Methods (C # Programming Guide)). Variables captured in this manner are stored for use in lambda expressions, even if in other cases these variables go out of scope and are garbage collected. You must explicitly assign an external variable before you can use it in a lambda expression. The following example shows these rules:

C#

delegate bool D ();

delegate bool D2 (int i);

Class Test

{

D del;

D2 Del2;

public void TestMethod (int input)

{

int j = 0;

Initialize the delegates with lambda expressions.

Note access to 2 outer variables.

Del'll is invoked within this method.

del = () = {j = 10; return j > input; };

Del2 'll is invoked after TestMethod goes out of scope.

Del2 = (x) + = {return x = = j;};

Demonstrate value of J:

Output:j = 0

The delegate have not been invoked yet.

Console.WriteLine ("J = {0}", j); Invoke the delegate.

bool Boolresult = del ();

Output:j = Ten B = True

Console.WriteLine ("J = {0}". b = {1} ", J, Boolresult);

}

static void Main ()

{

Test test = new test ();

Test. TestMethod (5);

Prove that Del2 still have a copy of

Local variable J from TestMethod.

BOOL result = Test.del2 (10);

Output:true

Console.WriteLine (result);

Console.readkey ();

}

}

The following rules apply to the range of variables in a lambda expression:

    • The captured variable will not be garbage collected until the delegate referencing the variable is eligible for garbage collection.
    • Variables introduced within a lambda expression are not visible in the external method.
    • A LAMBDA expression cannot capture a ref or out parameter directly from an enclosing method.
    • A return statement in a LAMBDA expression does not cause the enclosing method to return.
    • If the target of a jump statement is outside the block, the lambda expression cannot contain a goto statement, break statement , or continue statement that is inside the lambda function. Similarly, if the target is inside a block, it is also an error to use a jump statement outside the lambda function block.

C # Language Specification

For more information, see the C # Language specification. The language specification is the authoritative material for C # syntax and usage.

Important chapters

C # 3.0 Cookbook, third Edition:more than (solutions for C # 3.0 programmers, Events, and LAMBDA delegates

Please see

Reference

Anonymous methods (C # Programming Guide)

Is (C # Reference)

Concept

C # Programming Guide

Expression trees (C # and Visual Basic)

Other resources

LINQ (Language-Integrated query)

Visual Studio-C # example (see LINQ Sample query files and XQuery programs)

Recursive lambda expression

The [U1] name is not the function itself, just remember the name of the delegate. (The court commissioned the lawyer service, the real plaintiff defendant in the back.) )

The [U2] function is too complex, and a LAMBDA expression is an anonymous expression of a function.

[U3] represents a special symbol for LAMBDA expressions, C # does not support pointers, pointers are unsafe, and delegates are secure.

Lambda expression (C # Programming Guide)

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.