并发解决方案模型——Actor 模型
现在我们的 CPU 的技术,很难直接提高 CPU 的运行速度。现在我们都是通过增加核心数来提供 CPU 运算速度。我们在编写并发编程的时候,经常会遇到问题,特别是多线程下发现问题,调试问题都是很困难的。那么 Actor 模型就能很好的解决的问题,并且能很好的解决并发问题。
模型
actor 模型是处理并发竞争的模型概念。它定义了一些通用规则,说明系统的组件应该具有的行为和如何彼此交互。使用这个模型最著名的语言就是 Erlang。我将聚焦这个模型本身,而不是在不同的语言或库对其的实现。
Actors
一个 actor 是一个原语计算单位。即接受一个消息然后基于这个消息做一系列的计算。
这个很像我们面向对象语言:一个对象接受一个消息(方法调用)然后基于它接受的消息(就是我们调用的方法)依赖它去做一些事情。
actors 主要的不同就是它们彼此之间完全是隔离的,并且它们不会共享内存。值得注意的是一个 actor 能维护自己的私有状态,并且不受其他 actor 改变。
One ant is not ant
一个 actor 就没有 actor。它们在系统内出现。在 actor 模型中所有一切都是 actor,并且它们需要地址,以便一个 actor 能发消息给另一个 actor。
Actors 有邮箱(mailboxes)
理解这个是非常重要的,尽管多个 actor 能在同一时刻运行,一个 actor 能按顺序处理给定的消息。这意味如果你发送三个消息给相同的 actor,它将会在同一时刻运行。为了让这三个消息能被同时执行,你需要创建三个 actor 并发送一个消息给每个 actor。
消息能异步的发送给 actor,当它处理其他消息的时候,就必须得存储它们在某个地方。而邮箱(mailbox)就是用来存储消息的地方。
actors 通过发送异步消息来相互通信。这些信息都存储在 actor 的邮箱中一直到它们被处理。
Actor 做了什么
当一个 actor 接受到一个消息时,它可以做如下三件事:
- 创建更多的 actor
- 发送消息给其他 actor
- 指定如何处理下一条消息
前两点很简单明了,最后一个有点意思。
我之前有说过,一个 actor 能维护一个私有状态。“指定如何处理下一条消息” 最基本的意思是接受到下一个消息的状态。或者,更加清晰的说,actor 是如何改变状态的。
我们来想象一下一个 actor 的行为就像一个计算器。并且它被初始化为数字为 0 的状态。当这个 actor 接收到 add(1)
的消息时,它指定了它接收的下一个消息的状态,即 1。而不是修改它的原始状态。
容错
ErLang
引入了 “随它崩溃” 的理念。理论上是说你无需为了预防而编程,试图预测所有可能发生的问题并找到处理它们的方法,只是因为没有办法考虑每一个故障点。ErLang
所做的只是简单的让它崩溃, 但是,要让这个关键代码由一个唯一的职责是在崩溃发生时知道该做什么(比如将这个代码单元重置为稳定状态)的人来监督,而使这一切成为可能的就是 actor 模型。
每个代码都运行在进程内部(这基本上就是 Erlang 调用 actor 的方式)。这个进程是完全隔离的,这意味着它的状态不会影响任何其他进程。我们有一个监督程序,它基本上是另一个进程(所有的一切都是一个 actor ,记得吗?),当被监督的进程崩溃时,它会得到通知,然后可以对其进行处理。
这使它可以创建系统 “自愈” ,这意味着如果一个 actor 由于某种原因出现异常状态以及崩溃,监督者可以做些事情来把它放在一个一致的状态(有多种策略可以做到,最常见的只是重新启动 actor 初始化状态)。
分布式
actor 模型的另一个有趣的方面是,我向其发送消息的 actor 是在本地运行还是在另一个节点中运行并不重要。
想想看,如果一个 actor 只是这个带有邮箱和内部状态的代码单元,它只是响应消息,那么谁会关心它实际运行在哪台机器上呢?只要我们能把信息送到那里,我们就没事。
这允许我们创建利用多台计算机的系统,并帮助我们在其中一台计算机故障时进行恢复。
🔗:https://www.brianstorti.com/the-actor-model/