Java 8 |查找具有最大价值的地图条目

时间:2019-02-21 04:31:38

标签: java java-8 java-stream

我有个人模型Person [city,name]。我已将它们收集在“地图”中并按城市分组。我需要跟踪没有人居住的城市,并仅返回该条目作为地图的一部分。我试过了,而且它还在工作,但我想知道还有没有更好的方法。

Comparator<Entry<String, List<Person>>> compareByCityPopulation =
        Comparator.comparing(Entry<String, List<Person>>::getValue, (s1, s2) -> {
            return s1.size() - s2.size();
        });

HashMap mapOfMostPopulatedCity = persons.stream()
        .collect(Collectors.collectingAndThen(Collectors.groupingBy(Person::getCity), m -> {

            Entry<String, List<Person>> found = m.entrySet().stream().max(compareByCityPopulation).get();

            HashMap<String, List<Person>> hMap = new HashMap<>();
            hMap.put(found.getKey(), found.getValue());

            return hMap;
        }));

System.out.println("*City with Most no of people*");
mapOfMostPopulatedCity.forEach((place, peopleDetail) -> System.out.println("Places " + place + "-people detail-" + peopleDetail));

请建议我们如何在Java 8中更好地编写代码。

2 个答案:

答案 0 :(得分:5)

假设您有人员列表

List<Person> persons = new ArrayList<Person>();

然后首先根据城市将它们分组,然后在列表max中获得最大值的条目将返回Optional中的Entry,因此我不会使其复杂化只需使用HashMap来存储结果(如果结果以可选形式出现),否则将返回空的Map

Map<String, List<Person>> resultMap = new HashMap<>();

     persons.stream()
    .collect(Collectors.groupingBy(Person::getCity)) //group by city gives Map<String,List<Person>>
    .entrySet()
    .stream()
    .max(Comparator.comparingInt(value->value.getValue().size())) // return the Optional<Entry<String, List<Person>>>
    .ifPresent(entry->resultMap.put(entry.getKey(),entry.getValue()));

//finally return resultMap

答案 1 :(得分:5)

获取最大地图条目后,您必须将其转换为具有单个条目的地图。为此,您可以使用Collections.singletonMap()

Map<String, List<Person>> mapOfMostPopulatedCity = persons.stream()
    .collect(Collectors.groupingBy(Person::getCity)).entrySet().stream()
    .max(Comparator.comparingInt(e -> e.getValue().size()))
    .map(e -> Collections.singletonMap(e.getKey(), e.getValue()))
    .orElseThrow(IllegalArgumentException::new);

使用Java9,您可以使用Map.of(e.getKey(), e.getValue())通过一个条目来构建地图。