В сегодняшнем посте я хочу поделиться серией примеров, которые я разработал, пробуя последние функции Java 8 Stream API. В моем последнем посте я сравнил функции с доступными в LINQ, и для сегодняшнего поста я решил пойти немного дальше и попытаться использовать API для работы с моделью небольшого домена. Приведенные здесь примеры основаны на тех же примерах, которые представлены в проекте LambdaJ .
Модель данных
Для примеров я буду использовать следующую модель предметной области:
Вы можете увидеть полную реализацию всех примеров, разработанных здесь, загрузив следующий Gist .
Для примеров, представленных ниже, предположим, что в контексте кода всегда доступны три потока:
Stream<Person> persons
,Stream<Car> cars
,Stream<Sale> sales
,
Задача 1: Распечатать все автомобильные бренды
Из коллекции автомобилей печатаются все марки автомобилей.
StringJoiner brands = cars.map(Car::getBrand) .collect(toStringJoiner(",")); String allBrands = brands.toString();
Для этого примера я также использовал новый StringJoiner
класс.
Задача 2: Выбрать все продажи на Toyota
Из коллекции продаж выберите все, что связано с автомобилями Toyota.
List<Sale> toyotaSales; toyotaSales = sales.filter(s -> s.getCar().getBrand().equals("Toyota")) .collect(toList()); toyotaSales.forEach(System.out::println);
В этом примере я мог бы также использовать forEach
метод в потоке, чтобы распечатать все продажи. Я сделал это таким образом, чтобы проиллюстрировать, что можно собрать все элементы в потоке в список и оттуда мы можем их обработать. Но в идеале я должен был обработать элементы прямо в потоке.
Задача 3: Найти покупки самого молодого человека
Из коллекции продаж найдите все те, которые принадлежат самому молодому покупателю.
ToIntFunction<Entry<Person, List<Sale>>> byAge; byAge = e -> e.getKey().getAge(); byYoungest = sales.collect(groupingBy(Sale::getBuyer)) .entrySet() .stream() .sorted(comparing(byAge)) .map(Entry::getValue) .findFirst(); if(byYoungest.isPresent()) { System.out.println(byYoungest.get()); }
Задача 4: Найти самую дорогую продажу
Из коллекции продаж найдите самые дорогие из всех.
Optional<Sale> mostCostlySale; Comparator<Sale> byCost = comparing((ToDoubleFunction<Sale>)Sale::getCost) .reverseOrder(); mostCostlySale = sales.sorted( byCost ) .findFirst(); if(mostCostlySale.isPresent()) { System.out.println(mostCostlySale.get()); }
Задача 5: Сумма продаж от мужчин-покупателей и продавцов
Из коллекции продаж найдите сумму всех покупок / продаж, сделанных мужчинами.
doublesum = sales.filter(s -> s.getBuyer().isMale() && s.getSeller().isMale()) .mapToDouble(Sale::getCost) .sum();
Задача 6: Найти возраст самого молодого покупателя
Из коллекции продаж найдите возраст самого молодого покупателя, который купил более 40 000.
OptionalInt ageOfYoungest; ageOfYoungest = sales.filter(sale -> sale.getCost() > 40000) .map(Sale::getBuyer) .mapToInt(Person::getAge) .sorted() .findFirst(); if(ageOfYoungest.isPresent()) { System.out.println(ageOfYoungest.getAsInt()); }
Задача 7: Сортировка продаж по стоимости
Сортировать коллекцию продаж по стоимости.
Comparator<Sale> byCost= comparing((ToDoubleFunction<Sale>) Sale::getCost); List<Sale> sortedByCost; sortedByCost = sales.sorted( byCost ) .collect(toList());
Задача 8: Индекс автомобилей по марке
Из коллекции автомобилей, индекс автомобилей по марке.
Map<String,List<Car>> byBrand; byBrand = cars.collect( groupingBy(Car::getBrand ));
Задача 9: найти самый покупаемый автомобиль
Из коллекции продаж найдите самый покупаемый автомобиль.
ToIntFunction<Entry<Car,List<Sale>>> toSize = (e -> e.getValue().size()); Optional<Car> mostBought; mostBought = sales.collect( groupingBy(Sale::getCar) ) .entrySet() .stream() .sorted( comparing(toSize).reverseOrder() ) .map(Entry::getKey) .findFirst(); if(mostBought.isPresent()) { System.out.println(mostBought.get()); }