clojure的delay future promise

《Clojure编程》第4章笔记。

总的感觉,Clojure毕竟是基于JVM的在人间的工程化语言。不是纯的无状态纯函数的在神间的lisp。

作为后端语言,不可避免要处理计算中和代码执行时序、线程等方面的事情。

这方面Clojure有大量的概念和模式,让这些问题尽量地简化。和其他语言有类似的地方,但是确实有自己的特色。

这些东西基本上都是用def定义为模块ns下的var。类似全局可变var。(当然,定义在let里也是可以的

delay future promise

相同点:

1异步执行里面的语句,也就是不等待执行完,就继续执行下面的

2 都可以通过@ 和deref解引用取得结果。如果在没计算完之前解引用,产生阻塞效果。

   所以对解引用的执行者来说,不需要考虑被解引用的是什么。

解引用方式@ 和deref区别:

deref可以设置超时时间和返回值,@不行。

deref可以apply到整个序列,而@不行。

所以,简单情况用@ 需要考虑超时,或者集合操作的时候再用deref

delay可以保持结果:

(def d (delay (println "running...") :done!))
(println (deref d))
(println @d)
running...
:done!
:done!

delay接受的是一堆代码,把最后1个作为返回值:done! 

两次解引用,其实只计算了1次,第二次就直接用第一次计算后的结果了。适合1次计算,多次使用的场合。

如果d已经被求值,可以用(realized? d)进行判断

future

(deref (future (Thread/sleep 2000) :done!) 100 :impatient!)

隐式使用一个线程异步计算一些东西,然后解引用返回结果。

这里用了deref+超时 所以100ms就返回了:impatient!,不会等待2sec,返回:done!

promise

只声明,不包含如何计算的代码。

(def a (promise))

然后A通过deliver 投递数据,  B通过解引用得到结果。

作为一次性、单值的管道。

 

posted @ 2019-06-04 11:01  永远的幻想  阅读(373)  评论(0编辑  收藏  举报