-1

I have two distinct lists: list1 and list2, and I want to perform an action for each index where the elements have the same getName() value:

for (int i = 0; i < 5; i++) { 
    if (list1.get(i).getName().equals(list2.get(i).getName())) {
        // TODO
    }
}

Is there a way to do this using Java streams? I have tried the logic:

if (List1().stream().anymatch(x -> List2().stream().anymatch(y -> x.getName().equals(y.getName))))) {
    // TODO
}

This works, but first object(index) of list1 is compared with every object(index) of list2.

What I need is first object(index) of list1 to be compared with first of list2, second index to second and so on.

How can this logic be written using a stream instead of a for loop?

8
  • 1
    Please dont post code as images Commented Aug 2, 2021 at 13:54
  • Use an IntStream to generate the indices e.g. IntStream.range(0, 5), then use map, mapToObj or forEach as appropriate and access obj1.get(i) and obj2.get(i). Commented Aug 2, 2021 at 13:56
  • IntStream.range(0, a.length).mapToObj(i -> a[i].getName() == b[i].getName()).collect(Collectors.toList()); something like this? Commented Aug 2, 2021 at 14:01
  • What do you want after condition check. Are you going to store data in another list. please be specific toward your question and go to this link. Your question is explained here stackoverflow.com/questions/57252497/… Commented Aug 2, 2021 at 14:05
  • Hi sorry for the inconvenience, now added additional information to the question. kindly help me with this. Commented Aug 2, 2021 at 14:41

2 Answers 2

0

One solution is to use a third-party library that has the ability to zip pairs of streams into a single stream of pairs. Using this approach, the two streams would be zipped into a single stream containing the pairs of elements, the pairs with equal names would be retained via a call to Stream.filter(), and then finally the remaining filtered pairs of elements will have the action applied to them.

The Stack Overflow answer Zipping streams using JDK8 with lambda (java.util.stream.Streams.zip) contains various solutions for zipping two streams in this manner.

Guava

Google's Guava library provides the Streams.zip method:

Streams.zip(list1.stream(), list2.stream(), Map::entry)
        .filter(e -> e.getKey().getName().equals(e.getValue().getName()))
        .forEachOrdered(e ->
                System.out.println("Match: " + e.getKey() + ", " + e.getValue()));

StreamEx

The StreamEx library provides multiple zip methods, including StreamEx.zip and EntryStream.zip:

EntryStream.zip(list1, list2)
        .filterKeyValue((k, v) -> k.getName().equals(v.getName()))
        .forKeyValue((k, v) -> System.out.println("Match: " + k + ", " + v));
Sign up to request clarification or add additional context in comments.

Comments

0

One approach would be to stream over the indexes rather than the lists, and use List.get(i) to retrieve elements from each List.

IntStream.range(0, list1.size())
        .mapToObj(i -> Map.entry(list1.get(i), list2.get(i)))
        .filter(e -> e.getKey().getName().equals(e.getValue().getName()))
        .forEachOrdered(e ->
                System.out.println("Match: " + e.getKey() + ", " + e.getValue()));

or

IntStream.range(0, list1.size())
        .filter(i -> list1.get(i).getName().equals(list2.get(i).getName()))
        .forEachOrdered(i ->
                System.out.printf("Match at index %s: %s, %s\n", i, list1.get(i), list2.get(i)));

Note for this approach to be efficient, the lists must support fast (e.g. constant-time) random access. This would generally mean any list which implements the RandomAccess interface, such as ArrayList and Arrays.asList().

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.