这个@ngrx 示例中的 mergeMap 有什么好处?
What is the benefit of the mergeMap in this @ngrx example?
以下例子取自@ngrx example.
我是这样理解这个observable的。第一个 map
函数获取 payload
这是要添加的书,再次由 mergeMap
处理并保存到数据库。
原码:
@Effect()
addBookToCollection$: Observable<Action> = this.actions$
.ofType(collection.ActionTypes.ADD_BOOK)
.map((action: collection.AddBookAction) => action.payload)
.mergeMap(book =>
this.db.insert('books', [ book ])
.map(() => new collection.AddBookSuccessAction(book))
.catch(() => of(new collection.AddBookFailAction(book)))
);
下面的代码能和上面的一样吗?为什么需要 mergeMap
?
修改后的代码:
@Effect()
addBookToCollection$: Observable<Action> = this.actions$
.ofType(collection.ActionTypes.ADD_BOOK)
.map((action: collection.AddBookAction) =>
this.db.insert('books', [ action.payload ])
.map(() => new collection.AddBookSuccessAction(action.payload))
.catch(() => of(new collection.AddBookFailAction(action.payload)))
);
虽然@cartant添加了第一个答案,但答案和评论都很难理解。以下是我如何解释这段代码。
在原始代码中,this.actions$
是原始可观察对象。第一个 map
创建的 observable 是 outer observable。 inner observable 是由 this.db.insert
创建的 observable。因此这里有 3 个可观察值。
效果是addBookToCollection$
。
此代码(原始代码)的目的是生成一个 addBookToCollection$
类型 Observable<action>
的可观察对象。第一个 map
将创建一个 Observable<Book>
。这个类型不是什么效果,所以干脆不能以第一个map
结束。这个Observable<Book>
需要转换成Observable<Action>
。
我们可以使用switchMap
或mergeMap
将Observable<Book>
转换为Observable<action>
。这两个都将高阶可观察对象转换为一阶,如下所示:
Observable<Observable<Book> ----> Observable<Action>
switchMap
有利于异步操作,其中最新的内部可观察对象将被发射并且可以被@ngrx 订阅。但是 mergeMap
用于让所有内部可观察对象并发通过。因此它将允许用户选择的所有书籍从 this.db.insert
生成可观察值。本质上,mergeMap
从 map
获取 outer observable 并与 this.db.insert
的 inner observable 合并] 生成新的一阶可观察对象。
mergeMap
将 book
(action.payload
来自之前的 map
)并传递给 this.db.insert
。 this.db.insert
将通过 Observable<Action>
类型的 collection.AddBookSuccessAction(book)
生成一个动作。 map
的this.db.insert
returns那到mergeMap
和mergeMap
returns的第一个顺序Observable<Action>
.
Modified Code
出了什么问题?修改后的代码仅使用 map
,其中 returns 类型为 Observable<Observable<AddBookSuccessAction>>>
的高阶可观察对象。这不是正确的效果 addBookToCollection$
类型,应该是 Observable<Action>
.
以下例子取自@ngrx example.
我是这样理解这个observable的。第一个 map
函数获取 payload
这是要添加的书,再次由 mergeMap
处理并保存到数据库。
原码:
@Effect()
addBookToCollection$: Observable<Action> = this.actions$
.ofType(collection.ActionTypes.ADD_BOOK)
.map((action: collection.AddBookAction) => action.payload)
.mergeMap(book =>
this.db.insert('books', [ book ])
.map(() => new collection.AddBookSuccessAction(book))
.catch(() => of(new collection.AddBookFailAction(book)))
);
下面的代码能和上面的一样吗?为什么需要 mergeMap
?
修改后的代码:
@Effect()
addBookToCollection$: Observable<Action> = this.actions$
.ofType(collection.ActionTypes.ADD_BOOK)
.map((action: collection.AddBookAction) =>
this.db.insert('books', [ action.payload ])
.map(() => new collection.AddBookSuccessAction(action.payload))
.catch(() => of(new collection.AddBookFailAction(action.payload)))
);
虽然@cartant添加了第一个答案,但答案和评论都很难理解。以下是我如何解释这段代码。
在原始代码中,this.actions$
是原始可观察对象。第一个 map
创建的 observable 是 outer observable。 inner observable 是由 this.db.insert
创建的 observable。因此这里有 3 个可观察值。
效果是addBookToCollection$
。
此代码(原始代码)的目的是生成一个 addBookToCollection$
类型 Observable<action>
的可观察对象。第一个 map
将创建一个 Observable<Book>
。这个类型不是什么效果,所以干脆不能以第一个map
结束。这个Observable<Book>
需要转换成Observable<Action>
。
我们可以使用switchMap
或mergeMap
将Observable<Book>
转换为Observable<action>
。这两个都将高阶可观察对象转换为一阶,如下所示:
Observable<Observable<Book> ----> Observable<Action>
switchMap
有利于异步操作,其中最新的内部可观察对象将被发射并且可以被@ngrx 订阅。但是 mergeMap
用于让所有内部可观察对象并发通过。因此它将允许用户选择的所有书籍从 this.db.insert
生成可观察值。本质上,mergeMap
从 map
获取 outer observable 并与 this.db.insert
的 inner observable 合并] 生成新的一阶可观察对象。
mergeMap
将 book
(action.payload
来自之前的 map
)并传递给 this.db.insert
。 this.db.insert
将通过 Observable<Action>
类型的 collection.AddBookSuccessAction(book)
生成一个动作。 map
的this.db.insert
returns那到mergeMap
和mergeMap
returns的第一个顺序Observable<Action>
.
Modified Code
出了什么问题?修改后的代码仅使用 map
,其中 returns 类型为 Observable<Observable<AddBookSuccessAction>>>
的高阶可观察对象。这不是正确的效果 addBookToCollection$
类型,应该是 Observable<Action>
.