Two questions about forEach
Mike Duigou
mike.duigou at oracle.com
Wed Aug 8 19:47:55 PDT 2012
On Aug 8 2012, at 03:51 , Jose wrote:
> 2. Why forEach() returns void?. In this way the pipeline is sealed at the
> end, no more pieces can be attached to it.
> It would better returning the incomming iterable (its elements maybe
> modified by the lambda)
The problem is that forEach(), like into(), is an eager operation. For consistency with other eager operations forEach "consumes" the elements. If you find you are wanting to put forEach() in the middle of a pipeline you *probably* want to be using map instead which is properly lazy. forEach in the middle of a pipeline would remove the opportunity for lazy behaviour later in the pipeline.
Consider (imagining that forEach returned the stream) :
Set<ServerConnection> bar;
ServerConnection server = bar.stream().forEach(f-> f.refresh();}).filter(Foo::isActive).findFirst();
This snippet starts with a pool of server connections, refreshes each connection, filters out the active ones, and returns the first active.
Using forEach for the refresh() step means that *every* server is refreshed before even finding the first active server. This is probably a huge waste of effort. Rather than calling forEach it would be better to make the filter stage do the refresh (yes, it's a more complicated lambda, but the benefit is that only a smaller set of servers must be refresh()ed).
If there are examples of forEach in the middle of a pipeline that do make sense to you, feel free to ask for refactoring suggestions. :-)
Mike
More information about the lambda-dev
mailing list