What are lambda expressions? And what's the point of using them?

When I started using LINQ I saw that I could use the famous lambda expressions.

I even know that x => x * x is a lambda expression, but I couldn't explain to a colleague what they really are, and what the advantage of using them is.

Then I ask you:

What are lambda expressions? And what's the point of using them?

Author: Felipe Avelar, 2014-01-29

7 answers

What are lambda expressions?

Lambda expressions are those of Type A goes to B, primarily meaning a transformation. In C#, there are constant, and multiparameter lambdas.

In C#, A lambda expression, can be converted to:

  • a Delegate: is a compiled method, which can be executed, and passed as if it were a variable for anyone who needs it. Also called anonymous methods, because they do not have an identifier own.
  • a Expression<> that represents a tree of expressions that denote in data structure form the transformation that represents the lambda expression.

Use in the form of Delegate

When converted to a delegate, lambda can be passed as if it were a variable. A lambda produces a delegate of a specific type that depends on the context in which it is created.

Calls below generate type delegates different:

// delegate gerado do tipo Func<string, bool>
Func<string, bool> func = s => s == null;

// delegate gerado do tipo Predicate<string>
Predicate<string> pred = s => s == null;

Therefore each delegate of distinct type can be passed as if it were a common variable, and it is possible to call these methods like this:

pred("string to test");

All delegates, independent of the specific type, inherit from the Class Delegate.

Closures in delegates

Lambdas can present in its content, variables present in the method that constructs it, trapping this variable, in the form of a reference to it. This is also possible when building inline delegates.

int i = 0;
Action incrementa = () => i++;
incrementa();
// neste ponto a variável i, terá seu valor incrementado

This is a very powerful tool, and also dangerous, especially when used in loops, using the value of the iteration variable.

var listFunc = new Func<int>[10];
for (int it = 0; it < 10; it++)
    listFunc[it] = () => it;
// todos os elementos de listFunc retornam 10
// pois a variável it, neste ponto vale 10,
// e todos os delegates referenciam a mesma variável

Use in the form of expression

When talking about lambda expression, it is common to get beaten by this way of using them, but it is widely used by frameworks such as EntityFramework and MVC, both from Microsoft.

LINQ supports the IQueryable interface, which is based on in the use of lambdas transformed into data structure, which analyzes in order to create a query that can be executed in the database.

Just as these libraries do, it is possible to read this data structure generated from a lambda expression, using the classes present in the system namespace.Linq.Expressions .

Also, these lambdas in the form of Expression can be copied and changed, and after that compiled, being one of the ways to be generate dynamically executable code . You can also create an expression tree from scratch, dynamically generating integer methods, using the Compile method, present in the Expression<T> class.

Closures in expression trees

Expression trees can, like delegates, have in their code references to variables in the context in which they are constructed. Therefore, the reference to the variable is trapped in a node of the expression tree, which allows you to read the value of this variable, and maintain the semantics when compiling this expression tree.

 48
Author: Miguel Angelo, 2014-01-30 12:14:35

In essence, the advantage (in C#) of using them is being able to carry small functions as values.

In essence. Because they involve several other advantages.

In fact, x => x * x is not just a Lambda Expression, it is also known as an anonymous function, and can thus be used like any other function. You can even declare it like this:

Func<int, int> aoQuadrado = x => x * x;

And you could run it in a list, for example:

Enumerable.Range(1, 101).Select(aoQuadrado).ToList();

What would produce an IEnumerable with the squares of numbers from 1 to 100 (Enumerable.Range is unique, that is, it does not include the last number -- in this case, 101 -- in its operations).

This is equivalent to this (which is essentially the same thing, imperatively rather than functionally):

int AoQuadrado(int n)
{
    return n * n;
}

var quadrados = new List<int>();
for (int i = 0; i < 101; i++) quadrados.Add(AoQuadrado(i));

Incidentally, both methods and anonymous (or lambda) functions are functions, i.e. you could do this as well:

int AoQuadrado(int n)
{
    return n * n;
}

var quadrados = from i in Enumerable.Range(1, 101).Select(AoQuadrado).ToList();

Even because this is perfectly valid:

int AoQuadrado(int n)
{
    return n * n;
}

Func<int, int> aoQuadrado = AoQuadrado;

This is often called "first-class functions". Be the possibility to use functions as values, and thus be able to transport them more easily.

In Short: the main use of them is to be able to carry small functions as values, I would say.

 24
Author: André Leria, 2014-01-29 17:46:25

A lambda expression is a concise way to declare a function or subroutine. In an object-oriented world, it is quite similar to an object that has only one method.

There are two main advantages of using a lambda expression instead of a separately defined function or method:

  1. Simplicity. Why give a name to something that will only be used once?

  2. Lexical scope. Lambda functions can automatically use all variables of the current scope. For example:

    int y = 10;
    Func<int,int> f = (x => x + y);
    

    f it is a function that adds 10 to its argument. To do something equivalent using classes, we would need to create a new class, create a "y" field in that class, initialize that field in the class constructor, and pass 10 as a parameter when creating f. Using anonymous functions this all comes for free.

 13
Author: hugomg, 2014-01-29 17:54:25

In general lambda means passing a function as an argument to another function (definition given for JavaScript, and extends to all functional languages):

In free translation:

Lambda basically means using one function as an argument in a call to the other function. Lambda is a popular buzzword in functional programming and is widely used. The worst thing is, it is used as if everyone knows its real meaning. So if you see something like " Here we'll use a lambda expression", meaning they'll just be passing a function as an argument.

Visually, in psuedo-code, Lambda is represented by the symbol λ, the 11th letter of the Greek alphabet. You can also see variable names like lambda to indicate that it will receive a function.

Http://www.hunlock.com/blogs/Functional_Javascript#quickIDX3

The balcony in using them is to be able to have the lambda function executed at another time (it is so callbacks work in JavaScript).

For example, if it is necessary to do some computation inside/after a certain asynchronous event (such as an http request) is executed, we use a lambda expression (callback) in the function. Asynchronous events are important in the sense that they do not bar the program from running :)

 10
Author: JLuiz, 2020-06-11 14:45:34

William, This is a good question and one that would require a very extensive answer. It was trying to be brief, and for that it was leaving out a lot of things, okay?

What are lambda expressions?

Are by definition anonymous functions. I like to think of lambda expressions as math functions. You have the input parameters and the function body, for example: f (x) = x * 2

On the left side you define what the function receives, on the right side the which she does.

And what's the point in using them?

IMHO, the biggest advantage is being able to send functions as arguments to methods. The biggest example of this is in Linq, as you commented. See:

cidades.Where(x => x.Nome == "Florianópolis");

Let's see the method signature Where:

public static IQueryable<TSource> Where<TSource>(this IQueryable<TSource> source, Expression<Func<TSource, bool>> predicate);

The first argument is necessary because it is an extension method, so let's leave it aside for now. However, look at the second. It is an expression where its type is the type of the collection and it returns a boolean. In this way, any lambda expression that conforms to these constraints can be sent as a parameter.

The cool thing about this is that you can use all this potential in your code, you don't have to leave it only in the framework.

 7
Author: Andre Calil, 2014-01-29 17:52:45

Lambda expressions are nothing less than types of methods that you summarize without specifying the entire structure of a method. In fact, they return a reference to that encoded functionality.

This is very common in LINQ, since when you filter a collection you basically want to pass a method that decides whether or not an object should be among the filtered ones. For example, suppose you have a collection of objects as follows class

public class Cliente
{
    public int ClienteID { get; set; }
    public string Nome { get; set; }
    /* Outros membros */
}

And then you want only those that have ClienteID pair for example. So you use LINQ as follows:

var clientesFiltrados = listaClientes.where(verificaIdPar);

This verificaIdPar points to a method that can check if a ClienteID is even. But think about it a bit: to code this method normally, you'd have to put it in a class and all, reference it and then pass it to where and you'd hardly use it again. For this lambda expressions simplify your life, you can simply put a lambda expression instead, that it returns a reference to the method that has the functionality described in the lambda expression.

Also note that you can reference lambda expressions by variables of type delegate.And that's actually what these LINQ methods do: they expect a delegate that points to a method that filters, that selects, or any other operation, and then for simplicity we use lambda expressions.

 6
Author: SomeDeveloper, 2014-01-29 17:52:42

I believe that the concept is more important than how it is implemented.

Lambda expressions are functions, the way we learn in high school. For a given value of X, we will always get a given result Y. that is, given a Value X, we will always get the same value of Y. this behavior of an expression / function is called immutability, extremely important in functional languages, and that in programming minimizes the bugs related to effects and allows you to work with parallel and distributed programming more easily.

When a programming language implements the use of lambda expressions, it allows it to be treated as a value. That is, the function / expression can be put in a variable, passed as a parameter, and can usually be used in loops, in list of values, and the like, depending on how the language implements the resource.

 4
Author: Marcelo Haßlocher, 2014-01-30 12:37:39