I've been doing java for some time, due to corporate and personal inertia, mostly java 1.7. Recently I decided to start learning a bit more about the functional side o java, so I started playing with the Function interface and building a Validator that would check if a Map would match the Validator criteria. So that the Validator could be built programatically like
Usage:
Map<String, String> book = new LinkedHashMap<String, String>();
book.put("Title", "Leviathan Wakes");
book.put("Subject", "A proto molecule");
book.put("Category", "sci-fi");
book.put("TotalPages", "350")
final ResourceValidator filter = ResourceValidator.containsProperty("Title").and(ResourceValidator.containsProperty("Category"));
assert filter.apply(book);
This is code I've produced
public interface ResourceValidator extends Function<Map<String,String>,Boolean> {
static ResourceValidator containsProperty(String property) {
return resource -> resource.containsKey(property);
}
default ResourceValidator and(ResourceValidator other){
return resource -> this.apply(resource) && other.apply(resource);
}
}
So far it seems to be behaving as expected, what I can't understand is how the interface gets instantiated. The call to
final ResourceValidator filter = ResourceValidator.containsProperty("Title");
calls static method of the interface, how and where in the static method is ResourceValidator instantiated?
static ResourceValidator containsProperty(String property) {
return resource -> resource.containsKey(property);
}
I've been looking and I'm struggling to find an answer
You provided the implementation of those static methods. For example; when you created a lambda as resource -> resource.containsKey(property)
, what you essentially did was;
return new ResourceValidator() {
@Override
public Boolean apply(Map<String, String> resource) {
return resource.containsKey(property);
}
};
you implemented the apply
of ResourceValidator
function (is subtype of Function
interface, which is marked as a functional interface).
So now you could invoke it like;
ResourceValidator.containsProperty("foo").apply(Map.of("foo", "bar"));
You may have come across Java lambda expressions. Otherwise, this is quite comprehensive https://docs.oracle.com/javase/tutorial/java/javaOO/lambdaexpressions.html,