So it’s functional, right? Then why isn’t it a function? I’ll try to explain.
So since Java 8 we have the annotation @FunctionalInterface.
A functional interface is an interface that has just one abstract method (aside from the methods of
Object), and thus represents a single function contract. This “single” method may take the form of multiple abstract methods with override-equivalent signatures inherited from superinterfaces; in this case, the inherited methods logically represent a single method.
OK, but why not call it single abstract method. That actually what they called it before they switched to functional interface. Is this just a marketing buzzword because functional programming is in vogue?
Meaning of functional?
But it is not clear what functional even means in this context. A function is functional, right? A function is a relation that associates an input to a single output and each input should be related to exactly one output. Everything else isn’t really functional.
But those are all functional interfaces:
Consumer, Supplier, BiFunction
They all do not extend
Function. But the interface Function is actually used for such functions. All others are just types for lambdas, but not functional.
Functional languages such as Haskell only have functions that take one input value and map it to one output value. Multiple parameters are an illusion.
add(2,3) is actually:
add(2) returns a function that adds 2. Then 3 is applied to that function. This is known as partial application.
But Java doesn’t support that. It’s not a functional language.
What it really is.
It still is just an interface with a single abstract method. It’s also what the developers used:
They talk about SAMs, not about functional interfaces.
The idea was to have some pattern that allows to use an interface as the type of a lambda. And for that there must be some method that the lambda will implement. They use the term lambda all the time so why not call it LambdaInterface? There would at least be a connection to what it really is used for.
What it is not, but could have been.
What confuses me the most is that the annotation does not say anything about side effects. A lambda can have side effects and that is ok. But sometimes it is important to know whether a lambda has side effects or not. There is no clear distinction in Java 8. Just that some types say that they are intended to have a side effect (e.g. Consumer).
But how would a method be free of side effects?
- Don’t use any nonlocal variables.
- Only invoke other methods that are side-effect free.
I wonder if a compiler could actually check this reliably. And why javac doesn’t help more with this. It would be great to have another annotation for just that. Even if it’s just for documentation and so that other tools can use it.
Another annotation that I miss is
@Idempotent. I know I’m not the only one:
- https://github.com/cyriux/Patternity/ … /Idempotent.java
So all these projects use their own version of
@Idempotent. They already waited too long with