Java Language Lambda Expressions Method References


Example

Method references allow predefined static or instance methods that adhere to a compatible functional interface to be passed as arguments instead of an anonymous lambda expression.

Assume that we have a model:

class Person {
    private final String name;
    private final String surname;

    public Person(String name, String surname){
        this.name = name;
        this.surname = surname;
    }

    public String getName(){ return name; }
    public String getSurname(){ return surname; }
}

List<Person> people = getSomePeople();

Instance method reference (to an arbitrary instance)

people.stream().map(Person::getName)

The equivalent lambda:

people.stream().map(person -> person.getName())

In this example, a method reference to the instance method getName() of type Person, is being passed. Since it's known to be of the collection type, the method on the instance (known later) will be invoked.


Instance method reference (to a specific instance)

people.forEach(System.out::println);

Since System.out is an instance of PrintStream, a method reference to this specific instance is being passed as an argument.

The equivalent lambda:

people.forEach(person -> System.out.println(person));

Static method reference

Also for transforming streams we can apply references to static methods:

List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5, 6);
numbers.stream().map(String::valueOf)

This example passes a reference to the static valueOf() method on the String type. Therefore, the instance object in the collection is passed as an argument to valueOf().

The equivalent lambda:

 numbers.stream().map(num -> String.valueOf(num))

Reference to a constructor

List<String> strings = Arrays.asList("1", "2", "3");
strings.stream().map(Integer::new)

Read Collect Elements of a Stream into a Collection to see how to collect elements to collection.

The single String argument constructor of the Integer type is being used here, to construct an integer given the string provided as the argument. In this case, as long as the string represents a number, the stream will be mapped to Integers. The equivalent lambda:

strings.stream().map(s -> new Integer(s));

Cheat-Sheet

Method Reference FormatCodeEquivalent Lambda
Static methodTypeName::method(args) -> TypeName.method(args)
Non-static method (on instance*)instance::method(args) -> instance.method(args)
Non-static method (no instance)TypeName::method(instance, args) -> instance.method(args)
Constructor**TypeName::new(args) -> new TypeName(args)
Array constructorTypeName[]::new(int size) -> new TypeName[size]

* instance can be any expression that evaluates to a reference to an instance, e.g. getInstance()::method, this::method

** If TypeName is a non-static inner class, constructor reference is only valid within the scope of an outer class instance