Most of the IDE’s give you hints, that you could replace lambdas with method references. But there is a subtle difference between them.

I was refactoring commit at work on Vaadin application. To improve readability I started replacing lambdas with method references. After refactoring, and testing I noticed, that button click action resulted in NullPointerException.

Example

In this example, I’ll try to show the difference between lambda expression and method reference.

Lambda

package com.dovydasvenckus.lambda;

class MyCoolClass {
    public void doSomething() {
        System.out.println("My cool function invoked");
    }
}

public class Main {

    static MyCoolClass myCoolClass;

    public static void main(String[] args) {
        Runnable runnable = () -> myCoolClass.doSomething();
        myCoolClass = new MyCoolClass();
        runnable.run();
    }
}

Output:

My cool function invoked

Method reference

Runnable runnable = myCoolClass::doSomething;
myCoolClass = new MyCoolClass();
runnable.run();

Output:

Exception in thread "main" java.lang.NullPointerException
	at java.util.Objects.requireNonNull(Objects.java:203)
	at com.dovydasvenckus.lambda.Main.main(Main.java:14)

Summary

An object must be initialized before using method reference operator on it.

Lambdas are bit different, they can access a variable from outside their scope.