Javascript 地图vs concatMap
我还没有找到这个问题的答案,但是和之间有什么区别呢?具体来说,我举了一个让我非常困惑的例子:Javascript 地图vs concatMap,javascript,angular,rxjs,Javascript,Angular,Rxjs,我还没有找到这个问题的答案,但是和之间有什么区别呢?具体来说,我举了一个让我非常困惑的例子: const domainsObservable = this.auth.getAuthDomains() .shareReplay() .concatMap((authDomains) => authDomains.map((domain) => this.toDomain(domain, connectionsObservable))) .filter((authD
const domainsObservable = this.auth.getAuthDomains()
.shareReplay()
.concatMap((authDomains) => authDomains.map((domain) => this.toDomain(domain, connectionsObservable)))
.filter((authDomain) => this.isValidDomain(authDomain))
.toArray();
这是从一个服务调用一个方法,getAuthDomains()
,该服务刚刚返回了一个包含3个域的数组。当我使用上述实现时,我得到了一个由4个数组组成的数组,其中每个数组都有一个由3个域组成的数组。不知何故,它将响应中的数据量增加了四倍
然后,我切换到以下实现:
const domainsObservable = this.auth.getAuthDomains()
.shareReplay()
.map(authDomains => authDomains.map(domain => this.toDomain(domain, connectionsObservable)))
.map(authDomains => authDomains.filter(domain => this.isValidDomain(domain)));
这正好满足了我的需要——一个经过正确过滤的数组
那么,为什么切换到map
会显著改变结果呢?我的行动顺序重要吗
谢谢简单地说,这两个操作员执行以下操作:
-将每个值投影到一个不同的值中,该值在链的下游传播:map()
这与.map(v => v * 2)
基本相同Array.map()
-将每个值投影到一个可观察值中并订阅它。操作符始终只订阅一个内部可观察对象,因此如果源可观察对象更快地发出值,它们将被缓冲在concatMap()
: …或者通常在角度上,您会这样做:concatMap()
.concatMap(v => this.http.get(`whatever/${v}`))
subscribeToResult
函数实现的。请注意,如果您向其传递一个数组,它将迭代该数组并分别发出每个值:
这意味着您可以使用concatMap()。例如:
Observable.of(42)
.concatMap(v => [1, 2, 3])
.subscribe(console.log)
这将打印数字:
1
2
3
[1,2,3]
另一方面,如果您仅使用map
它只需进一步传递数组:
Observable.of(42)
.map(v => [1, 2, 3])
.subscribe(console.log)
这将打印数字:
1
2
3
[1,2,3]
因此,concatMap
有时仅用于解包来自源的数组,可通过concatMap(array=>array)
观察到,这正是代码中发生的情况
哪个更好取决于你。通常,由于性能原因,在阵列对象本身上执行简单操作(如map
或filter
)比在Rx链中解包和处理更容易