Click here to Skip to main content
Click here to Skip to main content

Lambda Expressions in C# and Java

, 10 Jul 2014 CPOL
Rate this:
Please Sign up or sign in to vote.
Lambda expressions were introduced in Java 8, and the concept is little bit different than in C#. We'll go through how these things are implemented in C# and in Java.

Introduction

Lambda expressions were introduced in Java 8, and the concept is little bit different than in C#. We'll go through how these things are implemented in C# and in Java. I'll write about related things as delegates and events which are not in Java, however, the observer and strategy pattern is also implemented in a different way.

C#

Delegates

Lambda expressions in C# are just a syntactic sugar to pass parameters to an anonymous method. Before lambdas delegate keyword could be used to achieve the same thing. Delegates has a couple of benefits, e.g. we can invoke multiple methods via a delegate and the important part is here, they behaves as a "method interface". Delegates provides the signature of methods which can be encapsulated. Delegates can be implemented as an anonymous method:

  delegate double CalculatorMethod(int a, int b);
        public void Execute()
        {
            CalculatorMethod multiply = delegate(int multiplicand, int multiplier)
            {
                return multiplicand * multiplier;
            };

            multiply(4, 8); // result is 32.0
        }

by lambda expression:

  CalculatorMethod multiply = (multiplicand, multiplier) =>
            {
                return multiplicand * multiplier;
            };

Almost the same syntax, just more simple.

What is the Real Benefit of Lambdas?

The most popular and useful utilization of Lambda expressions are related to Linq extension methods.

Consider this code:

var query = phoneBook.Where(p => p.Name.Contains("Jon"));

Here, we provided the strategy (by lambda) as an input parameter of "Where" method.

What does "Where" method do?

It does something like this, this is a simplified implementation (Linq to Objects):

public static IEnumerable<TSource> Where<TSource>(this IEnumerable<TSource> source,
                                                  Func<TSource, bool> predicate)
{
    foreach (TSource item in source)
    {
        if (predicate(item))
        {
            yield return item;
        }
    }
} 

This method is an extension method of IEnumerable<TSource> and accepts one input parameter:

Func<TSource, bool> predicate

This is a delegate which provides a method signature: Accepts object which type is TSource and returns a bool value. So when we previously provided that lambda, we have written an implementation for this delegate.

The "Where" method loops through the collection, and executes our lambda whatever it is and then returns only that records which meets the criteria.

Note: The implementation uses deferred execution, but that's not the point now.

Now we can see, that is a powerful tool to provide strategies easy way in action.

Java

Now there are Lambda expressions in Java too, however the delegate concept still does not exist.

So how does it work?

Anonymous classes

In Java, we can use anonymous classes, which is a similar concept, because the delegates were method interfaces and here we have class interfaces. So we can implement methods via a simple interface.

Interface which contains a simple method:

public interface ListMethods {
    List<String> SortFruits(List<String> original);
}

Here is a method which accepts the interface and then it will use its method to sort.
(Strategy pattern).
Our job is to provide the method of sort.

public List<String> StrategyTest(ListMethods strategy) {
    List<String> fruits = Arrays.asList("Apple", "Tomato", "Currant",
                "Cranberry");

    return strategy.SortFruits(fruits);
}

We can implement the method with an anonymous class:

public List<String> getFuitsAnotherWay() {

        //declaration of the anonymous class
        ListMethods anonymMethods = new ListMethods() {
            public List<String> SortFruits(List<String> original) {
                Collections.sort(original);
                return original;
            }
        };
        //pass it as a parameter
        return StrategyTest(anonyMethods);  

    }

Lambda Expressions

In Java 8, we can use lambda expression and as we can see the syntax is more simple than using an anonymous class.

public List<String> getFuitsAnotherWay() {
        return StrategyTest((fruitList) -> {
            Collections.sort(fruitList);
            return fruitList;
        });
    }
Limitation of Lambda Expression

Consider this interface:

public interface ListMethods {
    List<String> SortFruits(List<String> original);
    List<String> FilterFruits(List<String> original);
}

We can no longer implement this interface by lambda, because it can implement only functional interfaces. That is reasonable because the compiler can't decide which method is implemented exactly by the lambda.

This approach is quite similar to delegates in C#.

However, we can implement this interface by an anonymous class:

 public List<String> getFuitsAnotherWay() {
      ListMethods anonyMethods = new ListMethods() {
          public List<String> SortFruits(List<String> original) {
              Collections.sort(original);
              return original;
          }
            
          public List<String> FilterFruits(List<String> original) {
              if (original.size() > 2)
              original.remove(2);
              return original;
          }
      };
        
      return StrategyTest(anonyMethods);        
 }

Another interesting pattern which is related to this topic is observer pattern.

The observer pattern can be implemented by class interfaces, and there are many Java or C# examples about that, but in .NET framework, the observer pattern is implemented in Events and Eventhandlers by delegates.

Related article (Exploring the Observer Design Pattern) can be found at http://msdn.microsoft.com/en-us/library/ee817669.aspx.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)

Share

About the Author

Peter Silling

Hungary Hungary
No Biography provided

Comments and Discussions

 
GeneralMy vote of 4 PinprofessionalCatchExAs10-Jul-14 9:38 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.

| Advertise | Privacy | Terms of Use | Mobile
Web02 | 2.8.150123.1 | Last Updated 10 Jul 2014
Article Copyright 2014 by Peter Silling
Everything else Copyright © CodeProject, 1999-2015
Layout: fixed | fluid