2014-10-10 16 views
36

Chcę parallelize następujący kod snipped użyciu parallelStream:Strumień wartości logicznych, czy jest prawdziwy?

boolean anyTrue() { 
    for (Element e : setOfE) { 
    if (eval(e)) { 
     return true; 
    } 
    } 
    return false; 
} 

Will następujące prace na równoległych strumieni i regularne oceny zwarciem?

setOfE.parallelStream().map(e -> eval(e)).reduce(false, (a,b) -> a || b)) 

Odpowiedz

76

Streams API faktycznie ma pierwszej klasy obsługę zapotrzebowania:

setOfE.parallelStream().anyMatch(e->eval(e)); 

w przeciwieństwie do podejścia z reduce, to ma gwarancję oceny zwarć i optymalnego efektu równoległości.

12

Nie, redukcja nie obsługuje oceny zwarcia. Powodem jest to, że reduce po prostu otrzymuje dowolną implementację BinaryOperator i nie ma pojęcia o możliwości zwarcia danej operacji.

Ale można wykonać całą operację znacznie prostsze:

setOfE.parallelStream().filter(e -> eval(e)).findAny().isPresent() 

To po prostu wyszukuje dla dowolnego elementu, dla którego eval powraca true i findAny pozwala, aby zakończyć operację jak najszybciej jeden wątek napotkał mecz. Wynikowy Optional może być zapytany o bycie pustym, ponieważ nie jesteś zainteresowany konkretnym dopasowaniem Element.

Alternatywnie można użyć jako sugerowane przez komentarzu Marko Topolnik za:

setOfE.parallelStream().anyMatch(e -> eval(e)) 
Powiązane problemy