Ocaml Lwt.wait()



我有一个关于lwt的等待函数的问题,以及如何在我自己的自定义函数中使用它,该函数将返回一个lwt.t线程。首先让我们给你看一个例子。

open Lwt_io
open Lwt.Infix
let i, o = Lwt_io.pipe()
let get_int () =
let t, w = Lwt.wait() in
(*what do I do here to provide the sleeping thread*)
(*with a possible integer reply*)
Lwt_io.read_int(i) >>= fun i -> Lwt.wakeup w i;
t
let ans = get_int()

在上面的函数中,我调用wait来生成一个睡眠线程及其唤醒程序,但我不确定如何为睡眠线程提供一个可能的整数回复,并且仍然能够从get_int函数返回一个睡眠的线程。我提供了一行(Lwt_io.read_int(I)>>=乐趣I->Lwt.wakeup w I;)这似乎有效,但我不确定这是否是实现这一目标的正确方法。有任何指针、链接或评论吗?

注意:我这么问是因为在函数中添加Lwt_io.read_int(I)是多余的。我可以去掉get_int函数,只调用Lwt_io.read_int(I),但我很好奇如果没有冗余,你会怎么做。

首先,让我们切换到一个新的Lwt术语。根据Lwt库中接受的新术语,Lwt.wait函数返回一个promise和一个解析器。

这是一个非常低级的接口,通常用于实现更高级的接口。实际上,在您的情况下,get_int函数可以实现为Lwt_io.read_int

因此,为了进行实验,让我们实现一些更有意义的东西:

let wait () =
let promise, resolver = Lwt.wait () in
Lwt.async (fun () ->
Lwt_unix.sleep (Random.float 1.0) >|= 
Lwt.wakeup resolver);
promise

我们的wait函数返回一个promise,该promise将在随机延迟后实现。您可能会看到,有一个对Lwt.async的调用将执行thunk并在事件处理程序中异步执行,因此函数wait立即返回。当然,这个例子没有多大意义,因为具有相同语义的函数可以实现为:

let wait () = Lwt_unix.sleep 1.0

但这恰恰表明,wait函数仅用于实现Lwt基元。

当您需要解耦服务提供者和服务使用者时,可以合理地使用此接口。然后您可以使用Lwt.wait(或者更好的Lwt.add_task_*,例如

module Broker = sig 
type 'a t
val request : 'a t -> 'a Lwt.t
val provide : 'a t -> 'a -> unit
end = struct 
type 'a t = {mutable requested : 'a Lwt.u option}
let request broker = 
let promise, request = Lwt.wait () in
broker.requested <- Some request;
promise
let provide broker data = match broker.requested with
| None -> ()
| Some request -> Lwt.wakeup request data
end

当然,我们只是重新实现了邮箱(这是另一个证明,我们通常不需要那么低,因为一切都已经为我们完成了),但一般来说,当您有多个请求,并且您想实现自己的请求调度时,您可以使用这个低级别接口。

相关内容

  • 没有找到相关文章

最新更新