May Java group& order& top in a call chain? [英] May Java group&order&top in a call chain?

查看:69
本文介绍了May Java group& order& top in a call chain?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个POJO类

class A {
  public int id;
  public String groupName;
  public String getGroupName() { return this.groupName; }

  public int value;

  public A(int id, String groupName, int value) {
    this.id = id;
    this.groupName = groupName;
    this.value = value;
  }
}

并且id是唯一的,但groupName不是。然后我有一个A的列表。

And id is Unique, but groupName is not. Then I have a List of A.

List<A> list = new ArrayList<A>();
list.add(new A(1, "A", 3));
list.add(new A(2, "B", 5));
list.add(new A(3, "B", 7));
list.add(new A(4, "C", 7));

我想按groupName和value过滤列表,返回每个groupName的最大值。

I want filter the list by groupName and value, return the biggest value each groupName.

List<B> filtedList = list....
//filtedList contain
//A(1, 'A', 3) A(3, 'B', 7) A(4, 'C', 7)

我知道我可以像这样编码

I knew that I can code like this

Map<String, List<A>> map =  list.stream().collect(
    Collectors.groupingBy(A::getGroupName)
);

List<A> result = new ArrayList<A>();
map.forEach(
  (s, a) -> {
      result.addAll(
        deliveryOrderItems.stream().sorted(
          (o1, o2) -> o2.value.compareTo(o1.value)
        ).limit(1).collect(Collectors.toList())
      );
  }
);

问题是,我可以删除中间地图并在一个连锁电话中进行操作吗? / p>

And the question is, Can I remove the middle Map and do those operate in one chain call Like

//list.stream().groupBy(A::getGroupName).orderInGroup(A::value).topInGroup(1)


推荐答案

你可以做的是使用 groupingBy 与下游收集器。

What you can do is using groupingBy with a downstream collector.

在你的情况下, maxBy 将为你完成这项工作。这将为您提供 Map< String,Optional< A>> ,其中每个键根据您提供的比较器映射到可选的最大值。

In your case maxBy will do the job for you. This will give you a Map<String, Optional<A>> where each key is mapped to an optional greatest value according to the comparator you supply.

然后你得到地图的值,过滤它们以便你只得到非空的选项(在调用 get()可选上。您最终将收集的内容提取到列表

Then you get the values of the map, filter them so that you only get non-empty optionals (avoiding a NSEE when calling get() on an Optional). You finally extract their content that you collect into a List.

import static java.util.Comparator.comparingInt;
import static java.util.stream.Collectors.groupingBy;
import static java.util.stream.Collectors.maxBy;
import static java.util.stream.Collectors.toList;

...

List<A> resultList =
        list.stream()
            .collect(groupingBy(A::getGroupName, 
                                maxBy(comparingInt(A::getValue))))
            .values()
            .stream()
            .filter(Optional::isPresent)
            .map(Optional::get)
            .collect(toList());

根据您的示例,它输出:

Given your example, it outputs:

[A(1, A, 3), A(3, B, 7), A(4, C, 7)]

这篇关于May Java group&amp; order&amp; top in a call chain?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆