I would expected that both put operations throw a NullPointerException in the following code, but actually the lambda expression works fine while just the method reference throws a NPE.
public static void main(String... args) {
Object object = null;
Map<String, FuncInterface> map = new HashMap<>();
map.put("key1", () -> object.notify()); // works
map.put("key2", object::notify); // throws NPE
}
@FunctionalInterface
private interface FuncInterface {
public void someAction();
}
What is the difference?
The lambda is evaluated when it's called: if you called map.get("key1").someAction()
you would get a NPE.
The method reference is evaluated at creation time, i.e. when you first write object::notify
, which throws a NPE straight away.
In particular, the JLS 15.13.3 states:
Evaluation of a method reference expression is distinct from invocation of the method itself.
First, if the method reference expression begins with an ExpressionName or a Primary, this subexpression is evaluated. If the subexpression evaluates to null, a NullPointerException is raised, and the method reference expression completes abruptly.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With