【问题标题】:Why does the `CurrentThreadScheduler` launch immediately in outermost scope?为什么 `CurrentThreadScheduler` 会立即在最外层范围内启动?
【发布时间】:2020-04-02 00:31:44
【问题描述】:
open System.Reactive.Concurrency
open System.Reactive.Disposables
open System

let print i = printfn "%i on thread %i" i Threading.Thread.CurrentThread.ManagedThreadId
CurrentThreadScheduler.Instance.Schedule((), fun _ _ ->
    CurrentThreadScheduler.Instance.Schedule((), fun _ _ -> print 3)
    print 2
    Disposable.Empty
    )

print 1

输出:

2 on thread 1
3 on thread 1
1 on thread 1

为什么print 1 在最外层范围内最后运行?与CurrentThreadScheduler.Instance.Schedule((), fun _ _ -> print 3)不同,为什么前面的语句没有排队并立即执行?

【问题讨论】:

    标签: .net f# system.reactive


    【解决方案1】:

    CurrentThreadScheduler 将:

    1. 立即运行 thunk
    2. 如果 thunk 计划在 t 秒后进行,它将休眠 t
    3. 如果 thunk 已经在运行,它将被添加到队列中。

    遵循这 3 条规则:

    1. 第一个计划项目立即运行(打印 2)
    2. 第一个项目仍在运行,而第二个项目已排定,因此已排队
    3. 第一项完成,出队,第二项运行(打印 3)
    4. 调度器完成阻塞,所以最后一行执行(打印1)

    CurrentThreadScheduler implementation

    相比之下,ImmediateScheduler 只是“立即运行 thunk”。

    【讨论】:

    • 但是最外层范围内的程序不应该已经在队列中了吗?在我看来,当它在print 1 之前安排第一次重击时,某些东西已经在运行。还是我在这里狡辩太多,应该把它作为一个实现细节?
    • 但是队列在打印 1 时是空闲的。它是当前线程,所以它是同步的。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-08-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-10-28
    • 2015-01-03
    • 1970-01-01
    相关资源
    最近更新 更多