异步与编程语言的关系

异步方式必然会在线程上完成切换,而线程中维护的栈信息(调用关系、各层调用的局部变量等)会在每次异步调用时释放。大部分编程语言无法提供一种方式,将栈中的等效信息(称之为Continuation)友好的传递、保留。
JavaScript作为另类,在异步编程上出类拔萃。其原因可以用以下引用的两语说明(出自《JavaScript权威指南》):
“语言的闭包特性可以使得程序状态被继承,大大简化了异步编程。”
“在JavaScript中异步编程应用非常广泛,是历史中长期没有多线程支持造成的。”
JavaScript中闭包设计,特点在于变量的生命周期不是与调用行为绑定(对同一个方法对象调用多次,局部变量是同一份),而是与方法对象的定义绑定(执行方法定义语句时,并列及外层的局部变量便始终与方法对象绑定在一起了)。因此语句中,简单传递了一个方法对象,逻辑上定义方法对象时的局部变量也一同传递了。
据说Go语言,还可以做到不通过CPS样式(continuation passing style)的代码而实现大并发。猜测指的是Go原生支持协程,友好地传递了Continuation。
自命不凡的王垠写道过,“函数式语言只要支持 continuation,就会很容易的实现大并发,也许还会更高效,更好用一些。”
他还编写了一段40行代码,自称“上半生最重要的杰作”。据说代码的作用是将Lisp代码,自编译成CPS样式。
综上还看,异步方式的关键就是Continuation传递、保留了。但java对此支持显然不足,可以采用了一种没有设计感的实现:在回调子类中大量定义了成员变量,用于传递、保留异步调用时的局部变量(必要时,异步调用完的后续逻辑,可以抽象成的回调对象,同样由这些成员变量传递、保留)。

你可能感兴趣的:(异步与编程语言的关系)