简体   繁体   English

使用 delayElements 时程序在 Flux 完成之前终止

[英]Program terminates before Flux would finish when using delayElements

I'm learning about reactive programming but I have a doubt, I'm trying to execute the following code but I don't understand why if I add delayElements before subscribe the elements are not printed我正在学习反应式编程,但我有疑问,我正在尝试执行以下代码,但我不明白为什么如果我在订阅之前添加 delayElements 元素不会打印

Without delayElements the values are shown如果没有 delayElements,则显示值

import reactor.core.publisher.Flux;

import java.time.Duration;

public class PlayWithFlux {

    public static void main(String[] args){
        Flux<Integer> flux = Flux.just(1, 2, 3);
        flux.log().subscribe(System.out::println);
    }
}

With delayElements the elements are not shown使用 delayElements 元素不显示

import reactor.core.publisher.Flux;

import java.time.Duration;

public class PlayWithFlux {

    public static void main(String[] args){
        Flux<Integer> flux = Flux.just(1, 2, 3).delayElements(Duration.ofSeconds(1));
        flux.log().subscribe(System.out::println);
    }
}

Is there an explanation about this behavior?有没有关于这种行为的解释?

The problem here is that delayElements does as it says, it delays before emitting elements.这里的问题是delayElements正如它所说的那样,它在发射元素之前会延迟。

Calling subscribe is not a blocking event, its an async, or "fire and forget" operator.调用subscribe不是阻塞事件,它是异步或“即发即弃”运算符。

So what is actually happening is that you call subscribe then the main flow continues and ends the program, before any values have time to get emitted.所以实际发生的是你调用subscribe然后主流程继续并结束程序,在任何值有时间发出之前。

To solve this just quick and dirty is to delay the end of the program with for instance a call to Thread.sleep()为了快速而肮脏地解决这个问题,就是延迟程序的结束,例如调用Thread.sleep()

public static void main(String[] args){
    Flux.just(1, 2, 3)
        .delayElements(Duration.ofSeconds(1))
        .subscribe(System.out::println);

    // Delay program shutdown so we can watch the elements get printed
    Thread.sleep(5000);
}

If you are only using Flux.just and subscribe , then everything is executed on the main thread, so the program will terminate only after the Flux is finished.如果你只使用Flux.justsubscribe ,那么一切都在主线程上执行,所以程序只有在Flux完成后才会终止。

Once delayElements steps into the picture, the Flux is no longer executed on the main thread.一旦delayElements进入画面, Flux就不再在主线程上执行。 Internally delayElements switches to a so-called parallel scheduler, which is basically a thread pool.在内部, delayElements切换到所谓的并行调度程序,它基本上是一个线程池。 Since now the Flux is running on a different thread, the main thread will continue the execution without waiting for the Flux to finish and the program will terminate before the Flux would finish.由于现在Flux在不同的线程上运行,主线程将继续执行而不等待Flux完成,并且程序将在Flux完成之前终止。

Instead of using Thread.sleep , it is better to use one of the block... methods in this case.在这种情况下,最好使用block...方法之一,而不是使用Thread.sleep This way the program can finish right after the Flux finished:这样程序可以在Flux完成后立即完成:

public static void main(String[] args){
    Flux.just(1, 2, 3)
        .delayElements(Duration.ofSeconds(1))
        .doOnNext(System.out::println)
        .blockLast();
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM