Golang与Care-Language的主要区别在于Hoare

die*_*ter 16 concurrency go

看看Tony Hoare 1978年开创性论文中的例子:

Go的设计深受Hoare论文的影响.尽管Go与本文中使用的示例语言有很大不同,但这些示例仍然相当容易翻译.除了语法之外,最大的区别是Go将并发通信的管道明确地建模为通道,而Hoare语言的过程直接相互发送消息,类似于Erlang.Hoare在第7.3节中暗示了这种可能性,但是"每个端口在另一个进程中只与一个其他端口连接"的限制,在这种情况下,它将是一个主要的语法差异.

我糊涂了.

Hoare语言中的进程直接相互通信.Go例程也直接相互通信,但使用频道.

那么golang的局限性有什么影响呢.真正的区别是什么?

Ric*_*777 23

答案需要更全面地了解Hoare在CSP上的工作.他的工作进展可归纳为三个阶段:

  • 基于Dijkstra的信号量,Hoare开发了显示器.这些在Java中使用,除了Java的实现包含一个错误(参见Welch的文章Wot No Chickens).不幸的是,Java忽视了Hoare后来的工作.

  • CSP从中脱颖而出.最初,CSP需要从进程A到进程B的直接交换.Ada和Erlang使用这种集合方法.

  • CSP于1985年完成,当时他的书首次出版.最终版本的CSP包含Go中使用的频道.与牛津的Hoare团队一起,David May同时开发了Occam,这是一种故意将CSP融入实用编程语言的语言.CSP和Occam相互影响(例如在奥卡姆编程规则中).多年来,Occam仅在Transputer处理器上提供,该处理器的架构适合CSP.最近,Occam已开发出针对其他处理器的方法,并且还吸收了Pi演算以及其他通用同步原语.

因此,回答原始问题,将Go与CSP和Occam进行比较可能会有所帮助.

  1. 频道:CSP,Go和Occam都具有相同的语音语义.此外,Go可以轻松地将缓冲添加到频道中(Occam没有).

  2. 选择:CSP定义了内部外部选择.但是,Go和Occam都有一种选择:在Occam中选择 Go和ALT.事实证明,有两种CSP选择在实用语言中不那么重要.

  3. Occam的ALT允许条件保护,但是Go的选择没有(有一个解决方法:通道别名可以设置为nil来模仿相同的行为).

  4. 移动性:Go允许通过通道发送通道末端(以及其他数据).这创建了一个动态变化的拓扑结构,超出了CSP的可能范围,但米尔纳的Pi演算是用他的CCS开发的,用来描述这样的网络.

  5. 进程:goroutine是一个分叉进程; 它会在它想要时终止并且它没有父级.这不像CSP/Occam,其中流程是组合的.

一个例子在这里有所帮助:首先是Occam(nb缩进很重要)

SEQ
  PAR
    processA()
    processB()
  processC()
Run Code Online (Sandbox Code Playgroud)

去吧

go processA()
go processB()
processC()
Run Code Online (Sandbox Code Playgroud)

在Occam案例中,processC在processA和processB终止之前不会启动.在Go中,processA和processB非常快速地分叉,然后processC直接运行.

  1. 共享数据:CSP并不直接关注数据.但值得注意的是,Go和Occam之间在共享数据方面存在重要差异.当多个goroutine共享一组共同的数据变量时,竞争条件是可能的; Go的优秀竞赛探测器有助于消除问题.但Occam采取了不同的立场:在编译时阻止共享可变数据.

  2. 别名:与上述相关,Go允许许多指针引用每个数据项.奥卡姆不允许使用这些别名,因此减少了检测竞争条件所需的工作量.

关于Hoare的CSP,后两点更少关于May的Occam.但它们是相关的,因为它们直接涉及安全的并发编码.


rob*_*b74 5

这正是关键点:在Hoare的初始论文(以及Erlang)中使用的示例语言中,进程A直接与进程B对话,而在Go中,goroutine A与通道C对话,goroutine B在通道中侦听通道CIe 在Hoare的语言和Erlang中,它们是明确的,它们是隐含的.

有关详细信息,请参阅此文章.

  • 这在历史上并不完整,并且有点歪曲Hoare的工作. (3认同)