Javascript RxJS:如何不订阅初始值和/或未定义?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/28314882/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-23 01:36:58  来源:igfitidea点击:

RxJS: How to not subscribe to initial value and/or undefined?

javascriptrxjs

提问by Pipo

Being new to RxJS I often create a subject which holds values in the future, but is initially undefined. It can only be undefinedthe first time. I currently use a filterto skip undefinedvalues, but this is quite cumbersome as I do it everywhereas I need only once. (Maybe I do something wrong here?) Can I somehow subscribe to mySubjectonly after it got its first value via onNext?

作为 RxJS 的新手,我经常创建一个具有未来价值的主题,但最初是undefined. 这只能是undefined第一次。我目前使用 afilter来跳过undefined值,但这很麻烦,因为我在任何地方都这样做,因为我只需要一次。(也许我在这里做错了什么?)我可以mySubject在它通过 获得第一个值后以某种方式订阅onNext吗?

var mySubject = new Rx.BehaviorSubject(undefined);

mySubject.filter(function(value) {
  return value !== undefined;
}).subscribe(function(value) {
  // do something with the value
});

回答by Brandon

Use new Rx.ReplaySubject(1)instead of BehaviorSubject.

使用new Rx.ReplaySubject(1)代替BehaviorSubject

回答by lwohlhart

As mentioned by Willyou should be able to just skip the first value by using the skip operator:

正如Will所提到的,您应该能够使用跳过运算符跳过第一个值:

var mySubject = new Rx.BehaviorSubject(undefined);

mySubject.pipe(skip(1)).subscribe(function(value) {
  // do something with the value
});

回答by Billy

mySubject.pipe( skipWhile( v => !v ) );

mySubject.pipe( skipWhile( v => !v ) );

回答by danguilherme

For now I am using the filteroperator, but I don't know if it's a good solution:

现在我正在使用filteroperator,但我不知道这是否是一个好的解决方案:

var mySubject = new Rx.BehaviorSubject().filter(x => !!x);

mySubject.subscribe(value => { /* will receive value from below */);

mySubject.next('value');

mySubject.subscribe(value => { /* also receives the value */ });

回答by Mukundhan

Sometimes there will be a need for behaviourSubject, where the initial value does not matter and the current value is needed asynchronously while working inside a stream, Just in our case multiple chain promises are handled with user cancel while processing or during fetching the data from anywhere inside the stream.

有时需要behaviorSubject,其中初始值无关紧要,并且在流内部工作时异步需要当前值,就像在我们的情况下,在处理或从任何地方获取数据期间,用户取消处理多个链承诺溪流内。

This can be achieved using the following way.

这可以使用以下方式实现。

// for user related commands
this.commandSource = new BehaviorSubject(CONTINUE);
// filtering over initial value which is continue to make it as a different pipe
const stopPipe = commandSource.pipe(filter(val => val === STOP));
const fetchStream = Observable.fromPromise(this.fetchDetails);

merge(fetchStream, stopPipe).pipe(
 take(1),
 takeWhile(() => commandSource.value === CONTINUE),
 concatMap((response) => {
  // fetch Another response you can return promise directly in concatMap
  // return array of response [1 ,2 ,3];
  return this.fetchYetAnotherDetails;
 }),
 // we can add this to stop stream in multiple places while processing the response
 takeWhile(() => commandSource.value === CONTINUE),
 // triggers parallelly values from the concatMap that is 1, 2 , 3
 mergeMap(() => // massage the response parallelly using )
 finalize(() => thi
  commandSource.complete())
).subscribe(res => {
 // handle each response 1, 2, 3 mapped
}, () => {
 // handle error
}, () => {
 // handle complete of the stream
});

// when user, clicks cancel, this should stop the stream.
commandSource.next(STOP)

回答by Pat Niemeyer

I have found this frustrating in both RxJS and RxSwift. (Wanting a value subject combined with the ability to wait on the first value).

我在 RxJS 和 RxSwift 中都发现这令人沮丧。(想要一个价值主体与等待第一个价值的能力相结合)。

For JS I am currently just tucking away a filtered version in the subject, something like this:

对于 JS,我目前只是在主题中隐藏一个过滤版本,如下所示:

    let mySubject = new Rx.BehaviorSubject();
    mySubject.wait = mySubject.pipe(filter(v=>v!==undefined));

So the subject is still exposed for publishing but clients don't have to repeat the filter.

所以该主题仍然公开发布,但客户不必重复过滤器。

    mySubject.wait.subscribe((v)=>{...});