2016-09-06 97 views
0

我想对数组的每个元素执行异步操作并将其结果收集到字典中。我目前的做法是:RxJS - 收集异步操作结果

let asyncOp =() => Rx.Observable.interval(300).take(1); 
 
let dict = {}; 
 

 
Rx.Observable.from(['a', 'b']) 
 
    .mergeMap(el => asyncOp() 
 
       .map(asyncOpRes => dict[el] = asyncOpRes) 
 
       .do(state => console.log('dict state: ', dict)) 
 
) 
 
    .takeLast(2) 
 
    .take(1) 
 
    .map(() => dict) 
 
    .subscribe(res => console.log('dict result: ', res));
<script src="https://npmcdn.com/@reactivex/[email protected]/dist/global/Rx.umd.js"></script>

这基本上就像我希望,但它似乎是RxJs运营商的尴尬使用。所以,我需要用以下帮助:

  1. 避免字典突变(使用扫描()试过了,但不知道如何在这里使用它有一个mergeScan()方法,但同样在这里。)
  2. 使用takeLast并采取 - 应该可以简化?

我想我错过了一个RxJS操作符,它可以帮助我简化这个操作。

回答

2

“一个阵列的每个元件上执行异步操作并收集其在字典中的结果”的代码可以显著使用mergeMapreduce功能被简化:

import * as Rx from "rxjs/Rx"; 

const asyncOp =() => Rx.Observable.interval(300).take(1); 

Rx.Observable.from(["a", "b"]) 

    // Perform the async operation on the values emitted from the 
    // observable and map the emitted value and async result into 
    // an object. 

    .mergeMap((key) => asyncOp().map((result) => ({ key, result }))) 

    // Use reduce to build an object containing the emitted values 
    // (the keys) and the async results. 

    .reduce((acc, value) => { acc[value.key] = value.result; return acc; }, {}) 
    .subscribe((value) => { console.log(value); }); 
+0

感谢!这就是我一直在寻找的东西。 – dafing