Sunday, May 24, 2015

Lambda Expression and Functional Interface

Lambda expressions are one of the major features of Java 8 (Project Lambda). With this, Java adopts a feature of Functional Programming Language. This feature already present in other languages which runs on JVM (If you familiar of Scala, you might have noticed it). Anyway, we will see what is Lambda expression; how to use it and what are the advantages to use it.

Why Lambda Expressions

Lambda expression is a block of code written in a more readable and compact way. This piece of code can be executed later stage one or more times. This means, Lambda expression allows to pass a block of code as an argument to function or to a constructor. So far, we have been using Anonymous classes to do that. I will give you couple of most common examples on this and will convert them into Lambda expression.

Example - I

We write a anonymous thread using Runnable interface like this
        Runnable r = new Runnable() {
            public void run()
            {
                System.out.println("Anonymous Runnable Example");
            }
        };
        
        Thread t = new Thread(r);
        t.start();
If we use lambda expression, then the above code can be written as
        Runnable r2 = () -> System.out.println("Lambda Runnable Example"); 
        
        Thread t2 = new Thread(r2);
        t2.start();

Example - II

To sort list of elements (or an array), we use Collections.sort of Arrays.sort using a comparator like this
        String[] names1 = new String[]{"Java", "Scala", "Lisp"};
        Arrays.sort(names1, new Comparator<String>() {
            @Override
            public int compare(String o1, String o2)
            {
                return o1.compareTo(o2);
            }
        });
        
        for(String s : names1)
        {
            System.out.println(s);
        }
If we use lambda expression, the this code can be changed to
        String[] names2 = new String[]{"Java", "Scala", "Lisp"};
        
        Comparator<String> comparator = (s1, s2) -> { return s1.compareTo(s2);};
        Arrays.sort(names2, comparator); 
        
        for(String s : names1)
        {
            System.out.println(s);
        }
Similarly event listeners in Swing can also be written like this. Example ActionListener interface where you implement the action performed by an event.
Pretty easy, isn't it, now we will see more details on the lambda expression

Syntax

Syntax of lambda expression is also simple (as we saw in above examples).
Syntax: (arguments) -> { Code }
  • Lambda expressions takes one or more arguments separated by comma (,) 
  • Type of the arguments are optional
  • Code and Arguments are separated by the symbol (->).
  • Code is just a set of statements like we write in methods
  • The code needs to end with a return statement (if it needs to return a value). 
  • If there is only one statement in the code, then braces {} are optional 
See some more examples of Lambda expressions
Example : () -> System.out.println("Without arguments");
Example : (event) -> System.out.println("One argument without type");
Example : (String s1, String s2) -> {
            System.out.println("two arguments and return type");
            return s1.compareTo(s2);
          };

By looking at the code, examples and usage we can list the advantages of Lambda expressions as
  • It increase the readability of the code 
  • Reduces unnecessary boiler plate code
  • It also adds to the performance of the code using parallel processing. 

Functional Interface 

To incorporate the lambda expression into Java, designers introduced a new feature called Functional Interface. Functional Interface is an interface with only one method. To make it more semantic, we can add an annotation @FunctionalInterface. If we add more than one method, it will break the contract and it will no more be a functional interface, instead we can add default or static methods. Example of Functional Interfaces are
Examples
//Example 1 - Only one method
@FunctionalInterface
public interface FInterface
{
    public void method();
}

//Example 2 - with default method
@FunctionalInterface
public interface FInterface
{
    public void method();
    
    public default String printName()
    {
        return "Functional Interface";
    }
    
}
All the famous java interfaces like Runnable, Callable, Comparator etc.. are now functional interfaces. If you open the JavaDoc or code of these interfaces, you will see that these are annotated with @FunctionalInterface. See the samples below
//Comparator
@FunctionalInterface
public interface Comparator<T> {
...

//Runnable
@FunctionalInterface
public interface Runnable {
As i mentioned earlier in the post, lambdas are the most important and prominent feature of Java 8 which attracts most the developers, hope for you as well.

Thanks for reading and Happy Leaning!!!

No comments:

Post a Comment