Reputation: 159
interface MathOperation{
int operation1(int a, int b);
int operation2(int c, int d, int e);
}
public static int operate1(int a, int b, MathOperation mathOperation){
return mathOperation.operation1(a, b);
}
public static int operate2(int a, int b, int c, MathOperation mathOperation){
return mathOperation.operation2(a, b, c);
}
Why does the following code not work?
System.out.println("5 - 3 = " + operate1(5, 3, (a,b)->a-b));
System.out.println("5 + 3 + 4 = " + operate2(5, 3, 4, (a,b,c)->a+b+c));
Upvotes: 2
Views: 1783
Reputation: 37845
JLS 9.8 says this (paraphrased):
A functional interface is an interface that has just one abstract method. Instances of functional interfaces can be created with lambda expressions.
Since MathOperation
has more than one method, it cannot be created with a lambda expression.
Why can't that be? Well, because if we did this:
operate2( 1, 2, 3, ( (a, b) -> a + b ) );
What should happen, since we did not supply a definition of operation2
?
Use of the @FunctionalInterface
annotation will warn you of this, similar to how the @Override
annotation works:
/* causes a compilation error because
MathOperation is not a functional interface */
@FunctionalInterface
interface MathOperation {
int operation1(int a, int b);
int operation2(int c, int d, int e);
}
A more canonical definition of your sample code would be:
@FunctionalInterface
public interface IntTernaryOperator {
int applyAsInt(int a, int b, int c);
}
public static int operate1(
int a, int b,
IntBinaryOperator op
) {
return op.applyAsInt(a, b);
}
public static int operate2(
int a, int b, int c,
IntTernaryOperator op
) {
return op.applyAsInt(a, b, c);
}
JSE supplies a binary int operation, java.util.function.IntBinaryOperator
, but not a ternary operation, so we need to define our own.
Upvotes: 3