我有两个流:
getPost
是一个fromPromise
流,用于投放单个帖子。示例:author done
getPostsStream
流式传输给定作者的帖子列表。示例:a1 done, a2 done
我有3位作者,它也是一个流,示例:Bacon.fromArray(["a", "b", "c"])
。
我希望通过组合这些流来获取作者的帖子:
我有两个条件:
sample: a1--b1--c1--a2--b2--c2
getPost
流无法并行运行(导致许多http请求),sample: a1--b1--c1 should happen sequentially, it shouldn't burst.
以下是代码:
var getPost = function(author) {
return Bacon.fromPromise(new RSVP.Promise(function(resolve) {
setTimeout(function() { resolve(author + " done"); }, 1000);
}));
};
var getPostsStream = function(author) {
return Bacon.fromArray([1, 2, 3, 4]).flatMapConcat(function(v) {
return getPost(author + v);
});
};
var combinedFlatMap = Bacon.fromArray(["a", "b", "c"]).flatMap(function(v) {
return getPostsStream(v);
});
var combinedFlatMapConcat = Bacon.fromArray(["a", "b", "c"]).flatMapConcat(function(v) {
return getPostsStream(v);
});
//combinedFlatMap.log();
combinedFlatMapConcat.log();
我在作者流上做flatMap
并返回该作者的帖子流。这导致:
a1 done
b1 done
c1 done
a2 done
b2 done
c2 done
但是a1--b1--c1
突然出现,所以没有并发限制为1。
我做flatMapConcat
:
a1 done
a2 done
a3 done
a4 done
b1 done
b2 done
b3 done
b4 done
这可以按照我想要的顺序工作,但这次它不按顺序。
修改:
我玩过溪流,知道各种组合器是如何工作的。我最后的工作是两个流getPostsStream(author)
和author
流。我无法将这些与正确的顺序结合起来。哪个是a1 b1 a2 b2
,所以one post from each getPostsStream(author) and back
。你的例子是错的,尝试使用我的流:
Bacon.fromArray(["a", "b", "c"])
。getPostsStream(author)
。我需要的是,使用这两个流产生输出:
a1 done `wait 1 sec`
b1 done `wait 1 sec`
c1 done `wait 1 sec`
a2 done `wait 1 sec`
b2 done `wait 1 sec`
c2 done `wait 1 sec`
请注意,字母a b c
代表作者,而数字1 2 3
代表帖子。
如何在并发限制为1的情况下实现正确的顺序?
答案 0 :(得分:0)
您是否尝试过observable.flatMapFirst(f) flatMap
,但仅在以前生成的流已结束时生成新流。
修改:
开始简单。如果我们想要订单a1-a2-b1-b2
,那么我们首先按正确的顺序制作一系列事件。之后,我们flatMapWithConcurrencyLimit(1, getPost)
或flatMapConcat(getPost)
与getPost
(或其他Promise
- 返回功能)。
Bacon.fromArray(["a1", "a2", "b1", "b2"]).flatMapConcat(function (x) {
return Bacon.fromPromise(new Promise(function (resolve) {
console.log("start " + x + " " + new Date().getTime());
setTimeout(function () {
resolve(x + " " + new Date().getTime());
}, 2000);
}));
}).log("output");
结果:
start a1 1419796654587
output a1 1419796656589
start a2 1419796656589
output a2 1419796658591
start b1 1419796658592
output b1 1419796660593
tart b2 1419796660594
output b2 1419796662595
output <end>
另一个编辑
如果您从作者流(a-b-c-d
)开始,使用正确的排序(a1-b1-c1-d1-a2-b2...
)获取帖子流非常复杂。
a..b....c..d..
),则无法知道何时可以获取第一作者的第二篇文章。 fromArray
),那么尽可能长时间地停留在数组世界中要简单得多。在这种情况下,你可以使用下划线或lodash以正确的顺序排列提取物,然后进入异步的培根世界。var authors = ['a', 'b', 'c', 'd'];
var postIdsByAuthor = _.map(authors, function (a) {
return _.map([1, 2, 3, 4], function (i) {
return a + i;
});
});
var postIds = _.flatten(_.zip.apply(null, postIdsByAuthor));
// ["a1", "b1", "c1", "d1", "a2", "b2", "c2", "d2", "a3", "b3", "c3", "d3", "a4", "b4", "c4", "d4"]
异步案例可以解决,但不能使用单个内置组合器。然而,你的问题并不清楚。然而,合理的限制将是
- 以循环方式获取作者的帖子
- 让getPost
“工人”始终忙碌
所以一种情况是(水平轴上的时间)
authors: a....b........c....................
getPost: a1.a2.b1.a3.b2.c1.a4.b3.c2.b4.c3.c4
P.S。如果您或某人拒绝回答,请评论原因。