一段有意思的流处理代码

import java.util.HashMap;
import java.util.Map;
import java.util.stream.Collectors;

/**
 *  按value值对map进行排序,输出前k个key
 */
public class Main {

    public static void main(String[] args) {

        Map map = new HashMap(){{
            put("java",3);
            put("C++",4);
            put("Python", 2);
            put("C#", 0);
        }};

        int k = 2;

        System.out.println(map.entrySet().stream().sorted((o1,o2)->o2.getValue() - o1.getValue()).limit(k).map(
            Map.Entry::getKey).collect(Collectors.toList()).toString());
    }
}

解释

map变量声明时添加内容初始化
        Map map = new HashMap(){{
            put("java",3);
            put("C++",4);
            put("Python", 2);
            put("C#", 0);
        }};
sorted:
map.entrySet().stream().sorted((o1,o2)->o2.getValue() - o1.getValue())
// sorted 方法的函数签名
Stream sorted(Comparator comparator);
// Comparator 接口中的抽象方法
int compare(T o1, T o2);
boolean equals(Object obj);

我们知道,函数式接口要求接口里面只能有一个抽象方法,咋一看, Comparator 接口中有俩抽象方法,似乎不符合函数式接口的要求,但其实是符合的,因为第二个 euqals 抽象方法其实是继承自 Object,从 Object 继承的方法是不计入接口抽象方法数量的。所以,对于 Comparator 接口,我们只需要提供一个满足 compare 定义的函数方法就行了。

limit:
map.entrySet().stream().sorted((o1,o2)->o2.getValue() - o1.getValue()).limit(k)

limit 方法用于截取流中前 k 个元素,类似的还有 skip 方法,用于跳过前 k 个元素。

map:
map.entrySet().stream().sorted((o1,o2)->o2.getValue() - o1.getValue()).limit(k).map(
            Map.Entry::getKey)
// map 方法的函数签名 
 Stream map(Function mapper);
// Function 接口中的抽象方法
R apply(T t);

这里我们用了 Lambda 表达式方法的另一种形式,即不实例化类,直接从类中引用已有方法。

collect:
map.entrySet().stream().sorted((o1,o2)->o2.getValue() - o1.getValue()).limit(k).map(
            Map.Entry::getKey).collect(Collectors.toList())
//collect 方法的函数签名
 R collect(Collector collector);

collect 方法接收一个 Collector 对象,用于收集流,Collector 接口不是一个函数式接口。

你可能感兴趣的:(一段有意思的流处理代码)