1. 程式人生 > >Java8系列--Java Stream進階篇(流的操作)

Java8系列--Java Stream進階篇(流的操作)

1 流的操作的特點

1.1 流的操作的核心機制

  流的操作區別於傳統的集合操作的一大特點是,在Java 8中,流的操作是通過將外部迭代轉向內部迭代來實現的。
  在Java 8 Stream API中,流的操作實際上相當於對資料進行一系列的”篩選”操作,而”篩選”的標準實際上是一個個具體的”方法”,在Java 8 Stream中,是通過將這些篩選方法作為Stream流的一系列內部迭代的方法引數來實現的。
  以下面的例子展開講解。
  現在要求將車的價格在300百萬以上的車定義為高檔車。

  • 解決辦法:使用filter()方法進行篩選;
  • 篩選條件:car.getPrice() > 300即可;

      這裡,filter()方法是Stream的內部迭代方法,而car.getPrice() > 300是該filter()方法的一個內部引數。
      示例程式碼:

 List<Car> highPriceCar;
        highPriceCar = garage.stream()
                .filter(car -> car.getPrice() > 300)
                .collect(toList());

1.2 流的操作的優勢

  與傳統的集合操作相比,流的操作主要有以下兩個優勢:
  

  • 可並行操作,解決單執行緒的不足
  • 處理更具有針對性,處理效率高

2 流的常用操作結構圖

  流的操作主要分為”篩選和切片”“對映”“查找個匹配”“歸約”等四類操作,具體操作詳見下圖:
  流的操作

3 流的常用操作詳解

3.1 篩選和切片

1.謂詞篩選
  Stream介面支援filter方法,該操作會接受一個謂詞作為引數,並返回一個包括所有符合謂詞的元素的流。
  謂詞:一個返回值為boolean型別的函式。
  程式碼示例:
  

List<Car> lowPriceCar;
        lowPriceCar = garage.stream()
                .filter
(Car::isLowPriceCar)//isLowPriceCar()方法篩選低價車 .collect(toList());

  isLowPriceCar()方法:
  

private static boolean isLowPriceCar(){
  return garage.stream().allMatch(car -> car.getPricce() < 100);
}

2.篩選各異的元素
  流還支援一個叫做distict的方法,它會將序列中重複的元素篩選掉,從而返回一個元素各異的流。
  實現原理:根據流所生成元素的hashCode和equals方法實現。
  程式碼示例:
  

List<Integer> numbers = Arrays.asList(1, 2, 1, 3, 3, 2, 4);
        System.out.println("--- 篩除重複元素---");
        numbers.stream()
                .distinct()
                .forEach(System.out::println);

3.截短流
  流支援limit(n)方法,該方法會返回一個給定長度的流,該方法的引數是一個整數n,該引數即為限定的長度。篩選順序是從左到右,從前往後。
  程式碼示例:
  

List<Integer> numbers = Arrays.asList(1, 2, 1, 3, 3, 2, 4);
        System.out.println("--- 篩除重複元素---");
        numbers.stream()
                .distinct()
                .limit(2)//將前兩個不重複的數篩選出來
                .forEach(System.out::println);

4.跳過元素
  流支援的另一個方法skip(n)正好與limit(n)方法形成互補。
  skip(n)方法將前n個元素篩選掉,如果流中不足n個元素,則返回一個空流。
  程式碼示例:
  

List<Integer> numbers = Arrays.asList(1, 2, 1, 3, 3, 2, 4);
        System.out.println("--- 篩除重複元素---");
        numbers.stream()
                .distinct()
                .skip(2)//將前兩個不重複的數篩掉
                .forEach(System.out::println);

3.2 對映

3.3 查詢和匹配

3.4 歸約