2017-10-04 62 views
10

Bir akış nasıl tembel yaratılabilir? koleksiyon bazlı kod geçişi sırasında bu kalıbı içine birden fazla kez çalıştırmak: bildiğimiz gibiStream lazily oluştur

Collection collection = veryExpensiveCollectionCreation(); 
return Stream.concat(firstStream, collection.stream()); 

çıkan birleştirilmiş akışı tipik lazily işlenir. Bu nedenle, akış işlemesi, birleştirilen akışın birinci bölümünde durursa, pahalı koleksiyona hiç gerek yoktur.

Performans nedenleriyle, birleştirilmiş derleme aslında birleştirme işleminin ikinci bölümünün öğelerini yinelemeye çalışana kadar tüm koleksiyonun oluşturulmasını ertelemek istiyorum.

sözde kod

return Stream.concat(firstStream, new LazyStreamProvider() { 
    Stream<Something> createStream() { 
     return veryExpensiveCollectionCreation().stream(); 
    } 
); 

Edit gibi görünecektir: Ben akışlarına toplama oluşturma API tüm farkında akışı yapmak, iyi olurdu üstlenmeden farkındayım. Bununla birlikte, bu, bu durumda değiştirilemez bir API'ye sahip başka bir bileşenin parçasıdır.

+1

Eğer veryExpensiveCollectionCreation ('gövdesini değiştirebilir)' ya da sadece bir dönüş için aşırı 'Stream'? – Mena

+2

Can 'veryExpensiveCollectionCreation()' katı bir koleksiyon yerine tembel bir akışı döndürmek için değiştirilebilir mi? – puhlen

cevap

13
Belki

değil en iyi çözüm ancak bunu lazily inşa edilecek, böylece flatMap yönteminde koleksiyonunuzu oluşturabilirsiniz:

return Stream.concat(
     firstStream, 
     Stream.of(Boolean.TRUE).flatMap(ignoredBoolean -> veryExpensiveCollectionCreation().stream()) 
); 
+2

Sadece kafamı masanın üstüne vuruyorum, çünkü bu çok açık görünüyor. – Bananeweizen