Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What is the difference between using a Predicate or a function as a Java stream filter?

So assuming I use some random filter on a stream, the most straightforward way is to directly input the Predicate:

x.stream().filter(e -> e % 2 == 0)

As well I can simply make a reference and define the Predicate in advance:

Predicate<Integer> isEven = e -> e % 2 == 0;
...
x.stream().filter(isEven)

But I can as well use a function:

private static boolean isEven(Integer integer) {
    return integer % 2 == 0;
}
...
x.stream().filter(MyClass::isEven)

As far as I can tell, the Predicate is of course much more limited while the function might have side effects etc. But since people like Venkat Subramaniam use the latter solution, I really wonder: What are the main differences here?

like image 318
AdHominem Avatar asked Apr 22 '16 16:04

AdHominem


People also ask

What is the difference between predicate and function in Java?

Function interface is used to do the transformation.It can accepts one argument and produces a result. On the other side, Predicate can also accept only one argument but it can only return boolean value. It is used to test the condition.

What's the difference between a predicate and a function?

A Predicate is just a function that takes an object of some type and returns a boolean. A Function is a generalization which can return any type, not just Boolean 's.

What is filter and predicate in Java?

Java stream provides a method filter() to filter stream elements on the basis of given predicate. Suppose you want to get only even elements of your list then you can do this easily with the help of filter method. This method takes predicate as an argument and returns a stream of consisting of resulted elements.

What is predicate in Java stream?

Java Predicate Interface It is a functional interface which represents a predicate (boolean-valued function) of one argument. It is defined in the java. util. function package and contains test() a functional method.


1 Answers

No! Predicate is not really limited in comparison to a method reference! In fact, these things are all the same!

Just look at the filter() function signature: filter(Predicate<? super T> predicate)

And let's consider your examples:

x.stream().filter(e -> e % 2 == 0)

Predicate<Integer> isEven = e -> e % 2 == 0;
...
x.stream().filter(isEven)

The first one is just an inlined version of the latter.

private static boolean isEven(Integer integer) {
return integer % 2 == 0;
}
...
x.stream().filter(MyClass::isEven)

and here you can see Method References in action. MR are just a syntactic sugar allowing you to define Lambda Expression based on already existing functions.

At the end of the day all those expressions become the same implementation of Predicate functional interface.

Also, you can also perform side effects in your Lambda Expressions by using block syntax on the right side but it's generally not advised:

e -> {
    //side effects here
    return e % 2 == 0;
}
like image 83
Grzegorz Piwowarek Avatar answered Oct 16 '22 15:10

Grzegorz Piwowarek