Path: csiph.com!news.mixmin.net!aioe.org!.POSTED!not-for-mail From: =?UTF-8?Q?Arne_Vajh=c3=b8j?= Newsgroups: comp.lang.java.programmer Subject: Re: stream filter twice Date: Sat, 20 Feb 2016 22:20:51 -0500 Organization: Aioe.org NNTP Server Lines: 75 Message-ID: References: <04334e10-3bad-49dc-87d8-dc2f00f90807@googlegroups.com> NNTP-Posting-Host: ANasIS7Js9OyLQwgloeBLQ.user.gioia.aioe.org Mime-Version: 1.0 Content-Type: text/plain; charset=windows-1252; format=flowed Content-Transfer-Encoding: 7bit X-Complaints-To: abuse@aioe.org User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:38.0) Gecko/20100101 Thunderbird/38.6.0 X-Notice: Filtered by postfilter v. 0.8.2 Xref: csiph.com comp.lang.java.programmer:33857 On 2/20/2016 7:28 AM, Philipp Kraus wrote: > I'm using streams to filter some data. I just do this with > > > List x = myclasscollection.stream().filter( i -> i.filter() ).collect( Collectors.toList() ); > if (!x.isempty()) > return x; > > > List y = myclasscollection.stream().filter( i -> i.anotherfilter() ).collect( Collectors.toList() ); > if (!y.isEmpty()) > return y; > > return myclasscollection.stream().collect( Collectors.toList() ); > > So my question is, can optimize this with a stream operation. I need > to check each object of the collection, but only if no object exist, > I need to run the check with another filter. A change to filter( i -> > i.filter() || i.anotherfilter() ) or filter( i-> i.filter() ^ > i.anotherfilter() ) is not possible, because I need the empty check > of all results. > > In a best-case idea I need only one run with the stream and can build > the result list in one shoot. Did you have got any idea to optimize > this code? What is your goal? To produce easily understandable code? To save a few micro seconds? If the first then I think you current code is fine. If the second then you will need to be creative. Here is my attempt to be creative: import java.util.ArrayList; import java.util.Arrays; import java.util.List; import java.util.function.Predicate; import java.util.stream.Collectors; public class MultiProcessing { public static List original(List lst, Predicate p1, Predicate p2) { List x = lst.stream().filter(p1).collect(Collectors.toList()); if(!x.isEmpty()) return x; List y = lst.stream().filter(p2).collect(Collectors.toList()); if(!y.isEmpty()) return y; return lst; } public static List alternative(List lst, Predicate p1, Predicate p2) { List x = new ArrayList<>(); List y = new ArrayList<>(); lst.stream().forEach(v -> { if(p1.test(v)) x.add(v); if(x.isEmpty() && p2.test(v)) y.add(v); }); if(!x.isEmpty()) return x; if(!y.isEmpty()) return y; return lst; } private static void test(List lst, Predicate p1, Predicate p2) { System.out.println(original(lst, p1, p2)); System.out.println(alternative(lst, p1, p2)); } public static void main(String[] args) { List lst = Arrays.asList(1, 4, 9, 16); test(lst, v -> v > 2, v -> v < 2); test(lst, v -> v > 20, v -> v < 2); test(lst, v -> v > 20, v -> v < -2); } } Arne