這篇文章主要講解了如何使用Java 8 Stream和peek,內(nèi)容清晰明了,對此有興趣的小伙伴可以學(xué)習(xí)一下,相信大家閱讀完之后會有幫助。
成都網(wǎng)站制作、網(wǎng)站建設(shè)、外貿(mào)網(wǎng)站建設(shè)服務(wù)團隊是一支充滿著熱情的團隊,執(zhí)著、敏銳、追求更好,是創(chuàng)新互聯(lián)的標(biāo)準(zhǔn)與要求,同時竭誠為客戶提供服務(wù)是我們的理念。創(chuàng)新互聯(lián)把每個網(wǎng)站當(dāng)做一個產(chǎn)品來開發(fā),精雕細(xì)琢,追求一名工匠心中的細(xì)致,我們更用心!
簡介
java 8 stream作為流式操作有兩種操作類型,中間操作和終止操作。這兩種有什么區(qū)別呢?
我們看一個peek的例子:
Stream
stream = Stream.of("one", "two", "three","four");
stream.peek(System.out::println);
上面的例子中,我們的本意是打印出Stream的值,但實際上沒有任何輸出。
為什么呢?
中間操作和終止操作
一個java 8的stream是由三部分組成的。數(shù)據(jù)源,零個或一個或多個中間操作,一個或零個終止操作。
中間操作是對數(shù)據(jù)的加工,注意,中間操作是lazy操作,并不會立馬啟動,需要等待終止操作才會執(zhí)行。
終止操作是stream的啟動操作,只有加上終止操作,stream才會真正的開始執(zhí)行。
所以,問題解決了,peek是一個中間操作,所以上面的例子沒有任何輸出。
peek
我們看下peek的文檔說明:peek主要被用在debug用途。
我們看下debug用途的使用:
Stream.of("one", "two", "three","four").filter(e -> e.length() > 3) .peek(e -> System.out.println("Filtered value: " + e)) .map(String::toUpperCase) .peek(e -> System.out.println("Mapped value: " + e)) .collect(Collectors.toList());
上面的例子輸出:
Filtered value: three
Mapped value: THREE
Filtered value: four
Mapped value: FOUR
上面的例子我們輸出了stream的中間值,方便我們的調(diào)試。
為什么只作為debug使用呢?我們再看一個例子:
Stream.of("one", "two", "three","four").peek(u -> u.toUpperCase())
.forEach(System.out::println);
上面的例子我們使用peek將element轉(zhuǎn)換成為upper case。然后輸出:
one
two
three
four
可以看到stream中的元素并沒有被轉(zhuǎn)換成大寫格式。
再看一個map的對比:
Stream.of("one", "two", "three","four").map(u -> u.toUpperCase())
.forEach(System.out::println);
輸出:
ONE
TWO
THREE
FOUR
可以看到map是真正的對元素進(jìn)行了轉(zhuǎn)換。
當(dāng)然peek也有例外,假如我們Stream里面是一個對象會怎么樣?
@Data @AllArgsConstructor static class User{ private String name; }
ListuserList=Stream.of(new User("a"),new User("b"),new User("c")).peek(u->u.setName("kkk")).collect(Collectors.toList()); log.info("{}",userList);
輸出結(jié)果:
10:25:59.784 [main] INFO com.flydean.PeekUsage - [PeekUsage.User(name=kkk), PeekUsage.User(name=kkk), PeekUsage.User(name=kkk)]
我們看到如果是對象的話,實際的結(jié)果會被改變。
為什么peek和map有這樣的區(qū)別呢?
我們看下peek和map的定義:
Stream
peek(Consumer<? super T> action) Stream map(Function<? super T, ? extends R> mapper);
peek接收一個Consumer,而map接收一個Function。
Consumer是沒有返回值的,它只是對Stream中的元素進(jìn)行某些操作,但是操作之后的數(shù)據(jù)并不返回到Stream中,所以Stream中的元素還是原來的元素。
而Function是有返回值的,這意味著對于Stream的元素的所有操作都會作為新的結(jié)果返回到Stream中。
這就是為什么peek String不會發(fā)生變化而peek Object會發(fā)送變化的原因。
看完上述內(nèi)容,是不是對如何使用Java 8 Stream和peek有進(jìn)一步的了解,如果還想學(xué)習(xí)更多內(nèi)容,歡迎關(guān)注創(chuàng)新互聯(lián)行業(yè)資訊頻道。