java8中的steam流

 

1,創建stream流

        //1,通過Collection系列集合提供的stream方法
        List<String> list = new ArrayList<String>();
        Stream<String> stream1 = list.stream();

        //2,通過Arrays中提供的靜態方法stream 獲取數組流
        String[] strs = new String[10];
        Stream<String> stream2 = Arrays.stream(strs);

        //3,通過Stream類中的靜態方法 of
        Stream<String> stream3 = Stream.of("c", "s", "s");

        //4,創建無限流
          //迭代  iterate參數 (從 0 開始 ,每次+2)
        Stream<Integer> stream4_1 = Stream.iterate(0, x -> x + 2);
        stream4_1.forEach(System.out::println);

          //生成  參數使用的是供給型接口,無參,有返回值 下面是返回了一個隨機double類型的數值
        Stream.generate(() -> Math.random()).forEach(System.out::println);

2,操作流

stream流的操作分爲中間操作和終止操作,下面這個操作是從流中過濾大於3的內容

1,filter   接受Lambda,從流中排除某些元素

        List<Integer> list = Arrays.asList(1,2,3,4,5,6,7,8);

        //中間操作:不會執行任何操作
        Stream<Integer> stream = list.stream()
                .filter(e -> {
                    System.out.println("過濾 中間操作");
                    return e>3;
                });

        //終止操作:一次性執行全部內容,惰性求值
        stream.forEach(System.out::println);

如果不執行終止操作,中間操作是不會執行的

多箇中間操作可以連接起來形成一個流水線,除非流水線上觸發終止操作,否則中間操作不會執行任何的處理!
而在終止操作時一次性全部處理,稱爲“惰性求值”。

2,limit(n)  截斷流,使其元素不超過給定數量

        List<Integer> list = Arrays.asList(1,2,3,4,5,6,7,8);

        //中間操作:不會執行任何操作
        Stream<Integer> stream = list.stream()
                .filter(e -> {
                    System.out.println("過濾 中間操作");
                    return e>3;
                })
                .limit(2);

        //終止操作:一次性執行全部內容,惰性求值
        stream.forEach(System.out::println);

輸出結果就是  4  5

3,skip(n)  跳過元素,返回一個扔掉了前n個元素的流,如果流中元素不足n個,則返回一個空流。與limit互補

        List<Integer> list = Arrays.asList(1,2,3,4,5,6,7,8);

        //中間操作:不會執行任何操作
        Stream<Integer> stream = list.stream()
                .skip(5);

        //終止操作:一次性執行全部內容,惰性求值
        stream.forEach(System.out::println);

輸出結果就是 6 7 8

4,去重操作 distinct

        List<Integer> list = Arrays.asList(1,2,3,4,4,4);

        //中間操作:不會執行任何操作
        Stream<Integer> stream = list.stream()
                .distinct();

        //終止操作:一次性執行全部內容,惰性求值
        stream.forEach(System.out::println);

輸出結果 1 2 3 4

這裏去重是根據對象的hasCode和equals方法,所以如果要對實體類對象執行去重操作,需要重寫這兩個方法。

5,映射 

map 接收Lambda ,將元素轉換成其他形式或提取信息。接收一個函數作爲參數,該函數會被應用到每個元素,上,並將其映射成一個新的元素。

全部轉換爲大寫

        List<String> list = Arrays.asList("a","vvv","ddd");

        //中間操作:不會執行任何操作
        Stream<String> stream = list.stream()
                .map(x -> x.toUpperCase());

        //終止操作:一次性執行全部內容,惰性求值
        stream.forEach(System.out::println);

末尾加s

        List<String> list = Arrays.asList("a","vvv","ddd");

        //中間操作:不會執行任何操作
        Stream<String> stream = list.stream()
                .map(x -> x+"s");

        //終止操作:一次性執行全部內容,惰性求值
        stream.forEach(System.out::println);

flatMap 接收一個函數作爲參數,將流中的每個值都換成另一個流,然後把所有流連接成一個流

接受一個返回值是Stream的方法,把每次返回的流中的數據整合到一個流中。

6,排序

sorted 自然排序 按對象執行的方式進行排序,

        List<String> list1 = Arrays.asList("a","vvv","ddd");

        //中間操作:不會執行任何操作
        Stream<String> stream = list1.stream()
                .sorted();

        //終止操作:一次性執行全部內容,惰性求值
        stream.forEach(System.out::println);

輸出結果 a ddd vvv

 

定製排序 sorted(Comparator c)

這裏有個Person類,

public class Person {

    private Integer age;

    private double salary;

    public Person() {
    }

    public Person(Integer age, double salary) {
        this.age = age;
        this.salary = salary;
    }

    public Integer getAge() {
        return age;
    }

    public void setAge(Integer age) {
        this.age = age;
    }

    public double getSalary() {
        return salary;
    }

    public void setSalary(double salary) {
        this.salary = salary;
    }

    @Override
    public String toString() {
        return "Person{" +
                "age=" + age +
                ", salary=" + salary +
                '}';
    }
}

按年齡排序,如果年齡相同,按工資排序 

        List<Person> list = Arrays.asList(
                new Person(18,3939),
                new Person(38,9999),
                new Person(19,9988),
                new Person(38,99)
        );

        //中間操作:不會執行任何操作
        Stream<Person> stream = list.stream()
                .sorted((x,y) -> {
                    if(x.getAge() == y.getAge()){
                        return x.getSalary() > y.getSalary()? 1:-1;
                    }
                    return x.getAge().compareTo(y.getAge());
                });

        //終止操作:一次性執行全部內容,惰性求值
        stream.forEach(System.out::println);

3,終止操作

查找與匹配

        List<Person> list = Arrays.asList(
                new Person(18,3939),
                new Person(38,9999),
                new Person(17,9999),
                new Person(19,9988),
                new Person(38,99)
        );

        //是否匹配所有元素 此處返回false
        boolean b = list.stream().allMatch(e -> e.getAge() == 18);
        System.out.println(b);

        //至少匹配一個元素,此處返回true
        boolean b1 = list.stream().anyMatch(e -> e.getAge() == 19);
        System.out.println(b1);

        //流中是否沒有匹配元素,此處返回false
        boolean b2 = list.stream().noneMatch(e -> e.getAge() == 19);
        System.out.println(b2);

        //排序後獲取第一個元素
        Optional<Person> first = list.stream().sorted((x, y) -> x.getAge().compareTo(y.getAge())).findFirst();
        System.out.println(first);

        //獲取流中任意一個元素
        list.stream().findAny();

        //返回流中元素的總個數
        list.stream().count();

        //返回流中最大值 此處根據年齡比較
        Optional<Person> max = list.stream().max((x, y) -> x.getAge().compareTo(y.getAge()));
        System.out.println(max.get());

        //返回流中最小值 此處根據年齡比較
        Optional<Person> min = list.stream().min((x, y) -> x.getAge().compareTo(y.getAge()));
        System.out.println(min.get());

        //獲取最小的年齡
        Optional<Integer> age = list.stream().map(Person::getAge).min(Integer::compareTo);
        System.out.println(age.get());


        //獲取一個並行流,並行流會使用多個線程操作流,stream()獲取的是串行流,單個線程操作流
        list.parallelStream();

歸約:

 

        List<Integer> intList = Arrays.asList(
          1,2,3,4,5,6,7,8,9,10
        );

        /**
         * 第一個參數是從幾開始,第二個參數是執行的操作
         * x=0,y=1 x+y=1
         * x=1,y=2 x+y=3
         * x=3,y=3 x+y=6
         * x=6,y=4 x+y=10
         * x=10,y=5 x+y=15
         * x=15,y=6 x+y=21
         * x=21,y=7 x+y=28
         * x=28,y=8 x+y=36
         * x=36,y=9 x+y=45
         * x=45,y=10 x+y=55
         * 輸出結果爲55
         */
        Integer reduce = intList.stream().reduce(0, (x, y) -> x + y);
        System.out.println(reduce);

        List<Person> list = Arrays.asList(
                new Person(18,3939),
                new Person(38,9999),
                new Person(17,9999),
                new Person(19,9988),
                new Person(38,99)
        );

        //取出所有年齡,然後相加
        Optional<Integer> reduce1 = list.stream().map(Person::getAge).reduce(Integer::sum);
        System.out.println(reduce1.get());

收集:

        //取出所有年齡放到list集合中
        List<Integer> toList = list.stream().map(Person::getAge)
                .collect(Collectors.toList());

        //取出所有年齡放到set集合中
        Set<Integer> toSet = list.stream().map(Person::getAge)
                .collect(Collectors.toSet());

        //取出所有年齡放到hashSet集合中
        HashSet<Integer> toHashSet = list.stream().map(Person::getAge)
                .collect(Collectors.toCollection(HashSet::new));

        //獲取集合中元素總和
        Long count = list.stream().collect(Collectors.counting());

        //獲取年齡平均值
        Double avg = list.stream().collect(Collectors.averagingInt(Person::getAge));

        //獲取工資總和
        Double sum = list.stream().collect(Collectors.summingDouble(Person::getSalary));

        //獲取工資最大值的人
        Optional<Person> max = list.stream().collect(Collectors.maxBy((p1, p2) -> Double.compare(p1.getSalary(), p2.getSalary())));
        System.out.println(max.get());

        //獲取工資最小值的人
        Optional<Person> min = list.stream().collect(Collectors.minBy((p1, p2) -> Double.compare(p1.getSalary(), p2.getSalary())));
        System.out.println(min.get());

        //獲取元素個數、總和、最小值、平均值、最大值
        DoubleSummaryStatistics collect = list.stream().collect(Collectors.summarizingDouble(Person::getSalary));
        System.out.println(collect);
        //輸出結果:DoubleSummaryStatistics{count=5, sum=34024.000000, min=99.000000, average=6804.800000, max=9999.000000}

分組和分區

        //按年齡分組,年齡相同的是一組
        Map<Integer, List<Person>> 分組 = list.stream().collect(Collectors.groupingBy(Person::getAge));

        //按年齡分組後按工資分組,多級分組
        Map<Integer, Map<String, List<Person>>> 多級分組 = list.stream().collect(Collectors.groupingBy(Person::getAge, Collectors.groupingBy(x -> {
            return x.getSalary() > 3000 ? "高" : "低";
        })));

        //分區 滿足條件的一個區,不滿足條件的一個區
        Map<Boolean, List<Person>> collect1 = list.stream().collect(Collectors.partitioningBy(e -> e.getSalary() < 2000));

連接

        List<String> strs = Arrays.asList("a","b","cd");

        //連接所有內容
        String str = strs.stream().collect(Collectors.joining());
        System.out.println(str);
        //輸出:abcd

        //連接所有內容,中間加一個逗號隔開
        String str1 = strs.stream().collect(Collectors.joining(","));
        System.out.println(str1);
        //輸出:a,b,cd

        //連接所有內容,中間加一個逗號隔開,兩邊加上括號
        String str2 = strs.stream().collect(Collectors.joining(",","(",")"));
        System.out.println(str2);
        //輸出:(a,b,cd)

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章