It is common for the body to compute only a single expression (or expression statement) and return the result. Accordingly, a simpler form, expression lambdas, is provided:

ToIntFunction<String> lenFn = (String s) -> s.length();

Not only is this form syntactically more concise, but it is more obvious what the lambda does.

Because many expression lambdas consist only of passing the arguments (including possibly the receiver) to an existing method, a third form, method references, is provided:

ToIntFunction<String> lenFn = String::length;

While this form is not always more concise than the equivalent expression lambda, it is more transparent; it is clear that we are merely reusing an existing method.

All method references can be expressed as expression lambdas, and all expression lambdas can be expressed as statement lambdas, so the latter two forms are not strictly required. However, developers prefer to use the latter forms where possible, and this usually results in more readable code.

The same considerations can be applied to the declaration of methods: many method bodies consist entirely of evaluating a single expression or expression statement, and returning the result. We can apply the same syntactic options to method bodies as we do to lambda bodies, and achieve the same benefits.

Description

Traditionally, the declaration of a non-abstract method has a brace-delimited body containing statements, just like a statement lambda:

int length(String s) {
return s.length();
}

As with statement lambdas, it is common for a method body to compute only a single expression and return the result. We propose a concise form for such method bodies, modeled on the syntax of expression lambdas:

int length(String s) -> s.length(); // -> is "single expression form"

And, as with expression lambdas, many methods are merely wrappers around existing methods, so we appeal to the analogy with method references for another concise form:

When the body of a method has a concise form, the signature of the method provides a structural target type for the single expression or method reference. For the two concise bodies above, we would perform overload selection on String::length, looking for a method compatible with the target type of "String to int".

Any non-abstract, non-native method in a class or interface may be declared with a concise body. The bodies of constructors, instance initializers, and static initializers will not have a concise form. Whether a method body is concise has no effect on inheritance, overloading, or overriding.

The method reference form

The method reference form is particularly useful, as the idiom where a method merely delegates to another method is exceedingly common. For example, most factory methods merely delegate to an existing constructor:

This is not only more readable, but also less error-prone: the author need not repeat the argument list, and therefore avoids getting it wrong.

The single expression form

Concise method bodies lower the bar to pulling code into a new method, in the same way that var lowers the bar to pulling a subexpression into a new variable. Each use of the method is then a boost for readability, compared with having a smaller number of larger methods. In other words, concise method bodies improve factoring and reduce duplication. The single expression form is especially convenient for this, such as when used for a switch expression:

The single expression form allows the stylistic brevity and directness of expression lambdas to be enjoyed by more of the program. An expression lambda is convenient when you need a class instance with one concrete method:

button.addActionListener(ActionEvent e -> log(e.getWhen()));

but if you need more than one, then you're back to declaring an anonymous class with lots of { } "line noise":

In method fun1, the this::bar after -> evaluates to an instance of a functional interface embodying this method:

String bar(String s) { return null; }

In method fun2, the this::bar after = causes invocation of this method:

Function<String,String> bar() { return null; }

Background

C# 6 introduced "expression-bodied methods" to support the single expression form of a method body (but with a fat arrow => rather than a thin arrow ->). Kotlin also supports this form, with "single expression functions".