2015-09-29 17 views
9

Mam następujący pojedynczy strumień listBieg histogram strumień z Rx

A 
B 
C 
A 
D 
B 
A 
C 
D 

I z tego strumienia, chciałbym strumień uruchomiony Ilość na literę

(A,1) 
(A,1), (B,1) 
(A,1), (B,1), (C,1) 
(A,2), (B,1), (C,1) 
(A,2), (B,1), (C,1), (D,1) 
(A,2), (B,2), (C,1), (D,1) 
(A,3), (B,2), (C,1), (D,1)  
(A,3), (B,2), (C,2), (D,1) 
(A,3), (B,2), (C,2), (D,2)  

, czyli w każdej nowej litery , sumy są aktualizowane i emitowane.

Domyślam się, że ten problem jest dość agnostyczny, więc nie wahaj się zaproponować rozwiązania w wybranym przez ciebie języku.

Odpowiedz

11

ten sposób można to zrobić za pomocą RxJava:

final Observable<String> observable = Observable.just("A", "B", "C", "A", "D", "B", "A", "C", "D"); 
final Observable<LinkedHashMap<String, Integer>> histogram = observable.scan(new LinkedHashMap<>(), (state, value) -> { 
    if (state.containsKey(value)) { 
    state.put(value, state.get(value) + 1); 
    } else { 
    state.put(value, 1); 
    } 

    return state; 
}); 

histogram.subscribe(state -> { 
    System.out.println(state); 
}); 

wyjściowa:

{} 
{A=1} 
{A=1, B=1} 
{A=1, B=1, C=1} 
{A=2, B=1, C=1} 
{A=2, B=1, C=1, D=1} 
{A=2, B=2, C=1, D=1} 
{A=3, B=2, C=1, D=1} 
{A=3, B=2, C=2, D=1} 
{A=3, B=2, C=2, D=2} 
1

W RxJS może to być coś w rodzaju:

var letters = Rx.Observable.of('A', 'B', 'C', 'A', 'D', 'B', 'A', 'C', 'D'), 
    histogram = letters.scan(countL, Object.create(null)); 

histogram.subscribe(console.log.bind(console)); 

function countL(ls, l) { 
    if (!ls[l]) ls[l] = 0; 
    ls[l]++; 
    return ls; 
} 
+0

lub użyć [niezmienny mapę ] (https://facebook.github.io/immutable-js/docs/#/Map) jeśli nie chcesz, aby obserwatorzy z niższego poziomu mieli ulty zmieniły się spod nich nieumyślnie. – Brandon