Java Functional Interfaces and Lambda Expressions
Asked Answered
P

2

8

Given the following code, can someone please explain why the assertion returns true? Despite having searched around countlessly, I haven't been able to get any appropriate answer for why this might be the case, and what the Java feature(s) cause this behaviour and what restrictions / requirements I would have in similarly creating an interface such as this.

interface X {
  default int foo() {return 1;}
  String bar();
}

public class Exercise{
  public static void main(String[]arg){
    X foo1=()->"hello";
    assert (foo1.bar()).equals("hello");
  }
}
Poaceous answered 22/7, 2020 at 13:20 Comment(3)
Are you sure you running it with assertions enabled? -ea key in command line.Dispersal
@jpganz18 GitHub-style triple backticks are supported here now.Wilen
Yes I am sure that the code is being run with assertions enabled, and the assertion holds true. @talexPoaceous
F
19

A lambda expression is a concise way to create an instance of a functional interface, which is an interface with one abstract method. Here, X is a functional interface, with abstract method bar(). You could implement X with:

class XImpl implements X { 
    public String bar() { return "Foo"; }
}

X instance = new XImpl();

or an anonymous class

X anon = new X() { 
    public String bar() { return "foo"; }
};

or a lambda

X lambda = () -> "foo";

Each of these instantiates an implementation of X. What may be confusing you is the concision of the lambda; because X has only one abstract method, bar, you don't have to say you are implementing bar -- the compiler figures it out. Since bar() takes no arguments and returns String, the compiler ensures that the shape of the lambda is compatible with the shape of the sole abstract method.

Because an X has a bar() method, you can call it on each of these instances:

String s1 = instance.bar();
assertEquals(s1, "hello");

String s2 = anon.bar();
assertEquals(s2, "hello");

String s3 = lambda.bar();
assertEquals(s3, "hello");

and you get the same result for each.

Faculty answered 22/7, 2020 at 13:25 Comment(0)
C
4

Since method foo() has default implementation, you only need to specify bar() - which you do with X foo1 = ()->"hello".

So, your foo1.bar() returns hello.

UPD: My answer may be unclear, so I should note that 'foo' is not treated as an abstract method by compiler (that lets your interface X satisfy the requirements of declaring functional interface). Brian explains it clearer and more detailed in his answer.

Czechoslovak answered 22/7, 2020 at 13:23 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.