f1dave
f1dave

Reputation: 1297

Using streams to find the highest unique values

Let's say I have this simple Car object:

class Car {
  String id;
  String model;
  Integer price;  
}

Now I have a list of cars which might look like so:

{ Car(1, Commodore, 55000), Car(2, F150, 120000), Car(3, F150, 130000),
  Car(4, Camry, 50000), Car(5,Commodore,50000)}

I would like to filter any duplicate models out of the List, ensuring that I'm only keeping in the most expensive priced car of each duplicate, e.g:

{ Car(1, Commodore, 55000), Car(3, F150, 130000), Car(4, Camry, 50000) }

I believe that I can do this using the Streams API, but I'm just struggling to chain the right calls together.

In my head, I would imagine the pseudocode would be something like:

Trying to stitch that together got a bit messy though - any ideas?

Upvotes: 3

Views: 366

Answers (2)

fps
fps

Reputation: 34460

Use Collectors.toMap with a merge function that keeps the car with the max price:

Collection<Car> carsWithMaxPrice = cars.stream().collect(Collectors.toMap(
        Car::getModel,
        Function.identity(),
        (c1, c2) -> c1.getPrice() > c2.getPrice() ? c1 : c2))
    .values();

Upvotes: 2

Eran
Eran

Reputation: 393831

You can create a Map of the max valued car by model:

List<Car> cars = new ArrayList<> ();
Map<String,Optional<Car>> maxCarByModel =
  cars.stream ()
      .collect (Collectors.groupingBy (c -> c.model,
                                       Collectors.maxBy (Comparator.comparing (c->c.price))));

Upvotes: 2

Related Questions