我不是scalaz专家,但我会尽力帮助您。让我逐一回答您的问题:
1)有谁能分享使用scalaz编写并发/异步应用程序的经验,基本上如何正确使用它的async方法?
首先让我们看一下async
签名:
def async[A](listen: (A => Unit) => Unit): Future[A]
这可能一开始有点难懂,所以像往常一样,最好查看测试以了解可能的用例。在https://github.com/scalaz/scalaz/blob/scalaz-seven/tests/src/test/scala/scalaz/concurrent/FutureTest.scala中,您可以找到以下代码:
"when constructed from Future.async" ! prop{(n: Int) =>
def callback(call: Int => Unit): Unit = call(n)
Future.async(callback).run must_==
}
正如我们从签名Future.async
了解的那样,它只是使用签名(A => Unit) => Unit
的函数构建新的Future。这实际上意味着Future.async将函数作为参数,该函数对于给定的回调执行所有必需的计算并将结果传递给该回调。
需要注意的重要一点是,Future.async
本身不运行任何计算,它仅准备结构以稍后运行它们。
2)从源代码中我理解async不像标准future调用或scalaz中的fork/apply方法那样使用单独的线程,那么为什么它被称为异步?
你是正确的。只有fork
和apply
似乎使用线程运行任何内容,这很容易通过包含implicit pool: ExecutorService
的签名来注意到。我无法代表作者在这里发言,但我想异步与回调有关。这意味着您将使用异步回调,而不是阻塞在Future上以在最后获取结果。
3)这是否意味着为了获得scalaz的实际并发性,我总是要调用fork(now(...))或apply?
据我所知,是的。只需注意,当您使用语法Future(x)
创建Future时,您在这里使用了apply
方法,因此这是默认行为(这很好)。
如果您想更好地了解Scalaz Futures的设计,我可以推荐阅读《Scala函数式编程》。我相信该书是由主要的Scalaz贡献者编写的,第7章讨论了纯函数并行性库的API设计。它与Scalaz Future并不完全相同,但您可以看到许多相似之处。