I believe the OP is using a `Comparator`

to partition the input into equivalence classes, and the desired result is a list of members of the equivalence class that is the maximum according to that `Comparator`

.

Unfortunately, using `int`

values as a sample problem is a terrible example. All equal `int`

values are fungible, so there is no notion of preserving the ordering of equivalent values. Perhaps a better example is using string lengths, where the desired result is to return a list of strings from an input that all have the longest length within that input.

I don't know of any way to do this without storing at least partial results in a collection.

Given an input collection, say

```
List<String> list = ... ;
```

...it's simple enough to do this in two passes, the first to get the longest length, and the second to filter the strings that have that length:

```
int longest = list.stream()
.mapToInt(String::length)
.max()
.orElse(-1);
List<String> result = list.stream()
.filter(s -> s.length() == longest)
.collect(toList());
```

If the input is a stream, which cannot be traversed more than once, it is possible to compute the result in only a single pass using a collector. Writing such a collector isn't difficult, but it is a bit tedious as there are several cases to be handled. A helper function that generates such a collector, given a `Comparator`

, is as follows:

```
static <T> Collector<T,?,List<T>> maxList(Comparator<? super T> comp) {
return Collector.of(
ArrayList::new,
(list, t) -> {
int c;
if (list.isEmpty() || (c = comp.compare(t, list.get(0))) == 0) {
list.add(t);
} else if (c > 0) {
list.clear();
list.add(t);
}
},
(list1, list2) -> {
if (list1.isEmpty()) {
return list2;
}
if (list2.isEmpty()) {
return list1;
}
int r = comp.compare(list1.get(0), list2.get(0));
if (r < 0) {
return list2;
} else if (r > 0) {
return list1;
} else {
list1.addAll(list2);
return list1;
}
});
}
```

This stores intermediate results in an `ArrayList`

. The invariant is that all elements within any such list are equivalent in terms of the `Comparator`

. When adding an element, if it's less than the elements in the list, it's ignored; if it's equal, it's added; and if it's greater, the list is emptied and the new element is added. Merging isn't too difficult either: the list with the greater elements is returned, but if their elements are equal the lists are appended.

Given an input stream, this is pretty easy to use:

```
Stream<String> input = ... ;
List<String> result = input.collect(maxList(comparing(String::length)));
```

`max`

method to return? A`HashSet`

?firstelement that is maximal in the event of multiple maximal elements; only if the stream is unordered is it allowed to pick an arbitrary element.