2016-11-23 69 views
0

說是有其需要被第一修改,然後過濾收集:有沒有解決方法來從forEach方法「返回」流?

Collection<MyObject> collection = ... 
Stream<MyObject> dummyVariable = collection.stream(); 
dummyVariable.forEach(i -> i.callModifyingFunc(args)); 
return dummyVariable.filter(i -> i.isNeeded); 

因爲具有的forEach void返回類型是不可能寫代碼而不dummyVariable。有任何解決方法在一條鏈全部寫入:

Collection<MyObject> collection = ... 
return Stream<MyObject> dummyVariable = collection.stream().forEach(i -> i.callModifyingFunc(args)).filter(i -> i.isNeeded); 
+2

[map](https://docs.oracle.com/javase/8/docs/api/java/util/stream/Stream.html#map-java.util.function.Function-) – brian

回答

2

只要使用地圖,而不是的forEach到鏈流水線作業:

collection.stream() 
      .map(i -> i.callModifyingFunc(args)) 
      .filter(i -> i.isNeeded); 
+1

只有你想要放棄對哪些對象進行修改以及哪些不是...的控制 – Holger

2

如果返回Stream到主叫方,你有沒有控制終端操作最終由調用者鏈接。終端操作可能會處理所有元素,但也可能是短路,甚至可能是主叫方放棄流而根本不應用終端操作。

如果修改的目的只是記錄一個元素是否已被處理,peek是正確的選擇。

但是,如果你想修改適用於這兩種情況下的每一個元素,只是做了簡單明瞭的:

Collection<MyObject> collection = ... 
collection.forEach(i -> i.callModifyingFunc(args)); 
return collection.stream().filter(i -> i.isNeeded); 

如果你想確保當呼叫者開始一個終端的修改僅僅是由操作,這是一個比較複雜一點:

Collection<MyObject> collection = ... 
Spliterator<MyObject> sp = collection.spliterator(); 
return StreamSupport.stream(() -> { 
     collection.forEach(i -> i.callModifyingFunc(args)); 
     return sp; 
    }, sp.characteristics(), false) 
    .filter(i -> i.isNeeded); 

這將流處理開始之前執行權的所有元素的變形例中,終端操作的執行之前即

但是你應該重新考慮你的要求。在流處理聽起來有問題之前不得不修改所有元素。如果兩個客戶端獲得流,會發生什麼?

相關問題