Find which stream item does not match the specified predicate in allmatch

I want to know which element interrupted the predicate in the case of allmatch .

 List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5); boolean isEven = numbers.stream().allMatch(n-> n % 2 == 0); 

Here isEven is false , since element 1 does not execute the predicate.

I can use forEach on the stream to find which element is not working:

 numbers.stream().forEach(n -> { if (n % 2 != 0) System.out.println(n + "is Odd"); }); 

Is there a way to figure out which elements fail the predicate in allmatch when it returns false ?

+5
source share
6 answers

Remember that allMatch is a short circuit operation, which means that the thread API can return false without finding all elements that failed the test.

So, if you want to find all the faulty elements, you may need more work than just allMatch (as shown in other answers). However, if you only need to find one item that failed the test, use findAny as follows:

 Optional<Integer> odd = numbers.stream() .filter(n -> n % 2 != 0) .findAny(); boolean isEven = !odd.isPresent(); odd.ifPresent(x -> System.out.println(x + " is odd")); 
+5
source

In this example:

 Map<Boolean, List<Integer>> map = numbers.stream() .collect(Collectors.partitioningBy(x -> x % 2 == 0)); System.out.println(map); // {false=[1, 3, 5], true=[2, 4]} 

You can also simply register it, for example:

 boolean isEven = numbers.stream().allMatch(n -> { boolean test = n % 2 == 0; if (!test) { System.out.println("Failed = " + n); } return test; }); 

But this can lead to interesting results if you run it in parallel . The exit would be unpredictable. That is, isEven will still return the correct result, but what you see through Syso is not completely Syso . May be:

  Failed = 3 Failed = 1 Failed = 5 

And on another launch, it could be:

  Failed = 3 
+5
source

Try:

 List<Integer> notMatchElements = numbers.stream() .filter(n -> n % 2 == 0) .collect(Collectors.toList()); 

If the length of notMatchElements is 0 -> all match

Else β†’ your items do not match

0
source

You need to break this two actions down (filter and check all matches for two actions)

 List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5); List<Integer> notMatched = numbers .stream() .filter(n-> n % 2 != 0) .collect(Collectors.toList()); boolean isEven = notMatched.isEmpty(); 
0
source

I suggest using this approach:

 List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5); List<Integer> badNumbers = numbers.stream().filter(n -> n % 2 != 0).collect(Collectors.toList()); 

In this case, badNumbers will be empty if all elements satisfy n%2 = 0 , otherwise it will contain values ​​that do not.

0
source

Something needs to be clarified: a boolean not a Predicate . boolean is a noun but Predicate is a predicate . so your Predicate looks something like this:

 IntPredicate isEven = n -> n % 2 == 0; boolean numbersAreEven = numbers.stream().allMatch(isEven); 

IF you need to invert Predicate , you can use Predicate # negate , for example:

 IntPredicate isOdd = isEven.negate(); boolean numbersAreOdd = numbers.stream().allMatch(isOdd); 

IF you want to list all odd numbers, you should use Stream Filter # , for example:

 numbers.stream().filter(isOdd).forEach(System.out::println); 

IF you want to find the first odd number, you can use Stream # findFirst , for example:

 Number odd = numbers.stream().filter(isOdd).findFirst().orElse(null); 

IF you want to find the first odd number regardless of the order of the elements, you can use Stream # findAny , for example:

 Number odd = numbers.stream().filter(isOdd).findAny().orElse(null); 

Note: both Stream # findAny and Stream # findFirst are a terminal short-circuit operation , which means that it will exit after any intermediate operation .

0
source

Source: https://habr.com/ru/post/1268653/


All Articles