如何在Map.Entry中为Map值编写java 8 Comparator

时间:2017-03-31 17:38:40

标签: java java-8

这就是我所拥有的,我希望按照条目中的值降序排序。

Map<String, Outer> outer = Input
                          .entrySet()
                          .stream
                          .collect(toMap(Map.Entry::getKey, entry->{
                           List<Outer> inner = entry
                                    .getValue()
                                    .stream()
                                    .sorted(Comparator.comparingDouble(???))
                              })) ... (more lines of code.)

如何编写带有排序的比较器。 如果想在排序中执行以下操作

if (o1.getSomething() > o2.getSomething())
     return -1;
if (o1.getSomething() < o2.getSomething())
     return 1;
return 0;

获得List并进行排序后,它适用于我。

inner.sort((Outer o1, Outer o2) -> {
if (o1.getSomething() > o2.getSomething())
         return -1;
    if (o1.getSomething() < o2.getSomething())
         return 1;
    return 0;
});

但是有没有办法在条目中使用stream.sorted(“在这里使用相同的比较器逻辑”)。

Entry是一个ArrayList,带有一堆值。

entry:[{w:1},{w:2},{w:3},{w:4}];

所以我想对此进行反向排序,如下所示:

entry:[{w:4},{w:3},{w:2},{w:1}];

所以我得到的最终列表是按逆序排序的。

抱怨这个混乱。

5 个答案:

答案 0 :(得分:1)

如果您只是想获取Map的值并将它们放入已排序的List,则可以执行以下操作:

Map<String, Element> elMap = new HashMap<>();
elMap.put("3", new Element("3"));
elMap.put("2", new Element("2"));
elMap.put("1", new Element("1"));

List<Element> elList = elMap.values()
        .stream()
        .sorted((e1, e2) -> {
            return e1.getSortField().compareTo(e2.getSortField());
        })
        .collect(Collectors.toList());
System.out.println(elList);

在这里,Element是一个简单的POJO,其中包含一个名为String的{​​{1}}字段。 sortField需要sorted()。哪个是具有2个参数和Comparator返回类型的功能接口。对于给定的lambda,这是好的。

您也可以让您的元素实现int。然后你可以这样做:

Comparable

使用Element实现正确的接口

List<Element> elList = elMap.values()
        .stream()
        .sorted()
        .collect(Collectors.toList());

修改

  

它是Map中的一个列表,我正在尝试排序。并尝试在链条中对其进行排序。

这可以解释如下:

static class Element implements Comparable<Element> {
    //Constructor, field, getters
    @Override
    public int compareTo(Element o) {
        return this.sortField.compareTo(o.sortField);
    }
}

您在'Map.entrySet()'上流式传输并随意执行任何操作。根据您的问题将其收回到不同的Map<String, List<Element>> collected = elMap.entrySet() .stream() .peek(entry -> System.out.println("Performing arbitrary Map operations")) .collect(Collectors.toMap(Map.Entry::getKey, entry -> { return entry.getValue() .stream() .sorted(Comparator.comparingDouble(Element::getWeight)) .collect(Collectors.toList()); })); collected.entrySet() .forEach(entry -> { System.out.println(entry.getKey() + " : " + entry.getValue()); }); 时,您可以使用上面的示例再次流式传输并收集Map

答案 1 :(得分:1)

您可以定义Comparator,然后使用stream.sorted(),如下所示,并带有内嵌注释:

//Define comparator Lamda exp for Outer class
Comparator<Outer> outerComparator = (o1, o2) -> {
         if (o1.getValue() > o2.getValue())
                return -1;
          else if (o1.getValue() < o2.getValue())
                return 1;
            else 
              return 0;
   };


Map<String, Outer> output = Input.entrySet(). //get elements
        stream(). //get elements
        sorted( //sort elements by passsing outerComparator
        Map.Entry.<String, Outer>comparingByValue(outerComparator)
        .reversed())//reverse for descending order
        .collect(Collectors.toMap(Map.Entry::getKey, 
        Map.Entry::getValue));//collect to Map object

答案 2 :(得分:1)

据我所知,您的问题实际上就是如何创建排序列表作为地图中的值,并根据getSomething的返回值进行排序。

entry.getValue().stream()
    .sorted(Comparator.comparing(Outer::getSomething))
    .collect(toList())

将返回根据getSomething排序的列表。如果该方法返回一个double,那么您可以使用comparingDouble(Outer::getSomething)来避免装箱值。

答案 3 :(得分:1)

如果我猜对了,你想根据给定的比较器订购你的所有值(列表)。

如果是这种情况,则根本不需要创建流。使用Map的{​​{3}}方法就足够了:

// Orders Outer elements according to Outer's getSomething method 
// in descendant order (assumes getSomething returns a double value)
Comparator<Outer> yourComparator = 
    Comparator.comparingDouble(Outer::getSomething).reversed();

yourMap.replaceAll((k, v) -> {
        Collections.sort(v, yourComparator);
        return v;
    });

这利用replaceAll方法,该方法采用列表和比较器。

答案 4 :(得分:0)

所以这里的答案对我有用。

.sorted(reverseOrder(comparingDouble(Input::getSomething)))

谢谢大家,