<!----><!----><!----><!---->
<!---->
赵东炜:
Erlang
助你迎接多核时代的挑战
——写在
《
Erlang
程序设计》
出版之际
另辟蹊径——从容面对容错、分布、并发、多核的挑战。
作为一名程序员,随着工作经验的增长,如果足够幸运的话,终有一日,我们都将会直面大型系统的挑战。最初的手忙脚乱总是难免的,经历过最初的迷茫之后,你会惊讶地发现这是一个完全不同的“生态系统”。要在这样的环境中生存,我们的代码需要具备一些之前我们相当陌生或者闻所未闻的“生存技能”。容错、分布、负载均衡,这些词会频繁出现在搜索列表之中。经历过几轮各种方案的轮番上阵之后,我们会开始反思这一系列问题的来龙去脉,重新审视整个系统架构,寻找瓶颈所在。你可能会和我一样,最终将目光停留在那些之前被认为是无懈可击的优美代码上。开始琢磨:究竟是什么让它们在新的环境中“水土不服”,妨碍其更加有效地利用越来越膨胀的计算资源?
其实,早在多年以前硬件领域上的革命就已经开始,现在这个浪潮终于从高端应用波及常规的计算领域——多核芯片已经量产,单核芯片正在下线——这场革命正在我们的桌面上演。时代已经改变,程序员们再也不能继续稳坐家中装作什么事情也没发生,问题已经自己找上门来了。由单核
CPU
频率提升带来软件自动加速的时代已经终止,性能的免费大餐已经结束,“生态环境的变化”迫使代码也必须“同步进化”。锁、同步、线程、信号量,这些之前只是在教科书中顺带提及的概念,越来越多地出现在我们日常的编程中,接踵而至的各类问题也开始折磨我们的神经。死锁、竞态,越来越多的锁带来了越来越复杂的问题。
在多核
CPU
的系统上,程序的性能不增反降,或者暴露出隐藏的错误?
在更强的硬件平台上,程序的并发处理能力却没有得到提升,瓶颈在哪里?
在分布式计算网络中,不得不对程序结构进行重大调整,才能适应新的运行环境?
在系统的关键应用上,不得不为软件故障或者代码升级,进行代价高昂的停机维护?
……
<!----><!----><!---->
<!---->
中国互动出版网首发:
http://www.china-pub.com/301677
这一系列的问题,归根结底,都是因为主流技术体系在基本模型上存在着与并发计算相冲突的设计。换句话说,问题广泛地存在于我们所写的每一行代码中。在大厦初具规模时,却猛然发现每一块砖石都不牢固,这听来很有一些耸人听闻,但这种事并不罕见。
比如:
x = x + n
,即使是这个再常见不过的语句,也暗藏着烦恼的根源(你也可以把它称做共享内存陷阱)。从机器指令的角度来思考,这个语句可能做了这么几件事(仅仅只是在概念上)。
(1)
mov ax, [bp+x]
;将寄存器
ax
赋值为变量
x
所指示的内存中的数据。
(2)
mov bx, n
;将寄存器
bx
赋值为
n
。
(3)
add ax, bx
;将寄存器
ax
加
n
。
(4)
mov [bp+x],ax
;将变量
x
所指示的内存赋值为寄存器
ax
中的数据。
理论上,这是一个原子操作,在单核
CPU
下情况也确实如此,但在多核
CPU
下,就全然不同了。如果在每个核心上都有一个正在执行上述代码的进程(也就是试图对这个代码执行并行计算),问题就出现了。这里的
x
是在两个进程之间共享的内存。很明显,在第
(1)
步到第
(4)
步之间,需要某种机制来保证“某一时刻”只有一个进程正在执行,否则就会破坏数据的完整性。这也就意味着,这样的代码无法充分利用多核
CPU
的运算能力。也罢,咱们不加速就是了,但更糟糕的是,为了保证不出错,还需要引入锁的机制来避免数据被破坏。现有的主流技术体系全都建立在共享内存的模型之上,像
x = x + n
这样的代码几乎无处不在,但在多核环境下,每一处这样的代码(逻辑上的或者事实上的)都需要小心地处理锁。更糟糕的是,大量的锁彼此互相影响又会导致更为复杂的问题。这迫使程序员们在实现复杂的功能之余,还要拿出极度的耐心和娴熟的技巧来处理好这些沉闷和易错的锁,且不说是否可能,但这至少也是一个极为繁重的额外负担。
Erlang
为了并发而生。
20
多年前,它的创建者们就已经意识到了这一问题,转而选择了一条与主流语言完全不同的路(还有为数不多的另外几种语言也是如此)。它采用的是消息模型,进程之间并不共享任何数据,因而也就完全地避免了引入锁的必要。对于多核系统而言,完全无锁,也就意味着相同的代码在更多核心的
CPU
上会很容易具有更高的性能,而对于分布式系统,则意味着尽可能地避免了顺序瓶颈,可以把更多的机器无缝地加入到计算网络中来。甩掉了锁的桎梏,无疑是对程序员们的解放。
不仅如此,
Erlang
在编程模型上走得更远。它在语言级别提供了一系列的并发原语,通过这些原语,我们可以用进程+消息的模型来建模现实世界中多人协作的场景。一个进程表示一个人,人与人之间并不存在任何共享的内存,彼此之间的协作完全通过消息(说话、打手势、做表情,等等)交互来完成。这正是我们每一个人生而知之的并发模式!软件模拟现实世界协作和交互的场景——这也就是所谓的
COP
(面向并发编程)思想。
在错误处理上,
Erlang
也有与众不同的设计决策,这使得实现“容错系统”不再遥不可及。
COP
假设进程难免会出错——不像其他某些语言一样假设程序不会出错。它假设程序随时可能会出错,如果发生出错的情况,则不要尝试自行处理,而是直接退出,交给更高级的进程来对这种情况进行处理。通过引入“速错”和“进程监控”的概念,我们将错误分层,并由更高层的进程来妥善处理(比如,重启进程,或重启一系列进程)。有了这样的概念作为支撑,构造“容错系统”就会变得易如反掌。在这样的系统之下,软件错误不会导致整个系统的瘫痪,发现错误也无须停机就可直接更新代码,在配置了备份硬件之后,硬件的错误也不会影响服务的正常运行。这么做的结果相当惊人,使用
Erlang
的电信关键产品,达到了传说中的
99.9999999%
可用性(即
9
个
9
的最高可用性标准)。
Erlang
采用虚拟机技术实现,用它编写的程序可以不经修改直接运行在从手机到大型机几乎所有的计算平台之上。这是一项有着
20
多年历史的成熟技术,有着相当多的成熟库(
OTP
)和开源软件,这些资产使得它有极高的实用价值。
Erlang
本身也是开源软件,这扫清了对于语言本身生命力的疑惑。
Erlang
还是一个充满活力的语言,在它的社区,常常能够见到
Joe Armstrong
等语言的创建者在回答问题,这一点尤其宝贵。在熟悉了
Erlang
的思维方法和社区之后,很多人都发出了相见恨晚的感慨。
虽说对于并发而言,
Erlang
确实是非常好的选择,但这么多年以来,业界对于并发预料之中的增长却一直没有真正发生。此前,这类应用更多地局限在一些相对高端的领域,而
Erlang
身上浓厚的电信背景,又使得第一眼看来它似乎只适用于电信行业(实际情况远非如此)。长期以来
Erlang
的使用群体仅局限在一个狭小的技术圈子之内,它处于“非主流语言”的边缘位置已经很久了。这种情况直到最近才有所改观,最近两年,
Google
的成功使得其引为核心的大规模分布式应用模式广为人知,而多核
CPU
进入桌面也迫使“工业主流”开始认真对待并发计算。直到此时,解决这类问题最为成熟的
Erlang
技术,才因为其难以忽视的优势而引起人们的广泛关注。
从历史的眼光来看,在计算机语言的荣誉堂内,上演着一代又一代程序设计语言的繁荣和更替,潮来潮往让人难以捉摸。这与其说是技术,还不如说是时尚。对于
Erlang
这种有些怪异的小众语言来说,是否真的会成为“下一个
Java
”?实难预测,而且也不重要。但是有一点已经毫无疑问,那就是“下一代语言”至少也要像
Erlang
一样,处理好与并发相关的一系列问题(或者做得更好)。也许将来的
X++
(或
X#
)语言在吸收了它的精髓之后,又会成为新的工业主流语言。但即便如此,先跟随本书作者开辟的小径信步浏览这些饶有趣味的问题肯定也会大有帮助。
对于想要学习
Erlang
的读者,虽说语言本身相当简单,但想要运用自如也有一些难度。比如,在适应
COP
之后会觉得非常自然,但对于有
OOP
背景的程序员而言,从固有的思维习惯转换到
COP
和
FP
上(主要是和自己的思维惯性较劲)需要有一个过程。此外
OTP
和其他
Erlang
社区多年积累的财富(这些好比
JDK
、
EJB
之于
Java
)也需要一些时间才能被充分地理解和吸收。但这些有价值的资料大多零星地散落于邮件列表和独立的文档之中,给学习造成了很多不必要的麻烦。现在好了,有了
Erlang
创建者
Joe
Armstrong
分享到:
相关推荐
《Erlang和OTP实战》是一本专注于Erlang编程语言和OTP(Open Telecom Platform)框架的专业书籍。这本书深入浅出地介绍了Erlang在分布式系统、并发处理以及高可用性设计中的应用,同时结合 OTP 提供了强大的工具和库...
erlang文献及资料汇总 入门资料: erlang中文手册(R11B ...erlang VM基于多核处理器的可伸缩性特征 erlang VM内部数据共享机制 erlang 消息传递机制 文章地址:http://blog.csdn.net/mycwq/article/details/43115733
一系列技巧和窍门可帮助您了解故障的根源,以及各种不同的代码片段和实践字典,可帮助开发人员调试在Erlang中构建的生产系统。
读书笔记:ErlangOTP设计原则中文文档
《Erlang编程》是一本深入探讨Erlang语言的图书,主要面向对并发处理、分布式系统和高可用性有需求的开发者。Erlang是一种为构建大规模并发系统而设计的函数式编程语言,它源自爱立信,以其在电信行业的成功应用而...
**函数式编程**:Erlang是一种函数式语言,函数无副作用,强调纯函数和不可变数据,这有助于编写简洁、可预测的代码。 **动态类型**:Erlang是动态类型的,变量的类型在运行时确定,提供了灵活性。 **及早求值或...
erlang 并发 编程 开发 语言
- **海量存储**:对于需要处理大量数据的应用,Erlang的并发处理能力有助于提高数据处理效率。 - **网关代理服务器**:在网络中作为中间层,负责转发请求和响应。 - **异构系统粘合**:Erlang提供了多种接口(如NIF...
Erlang是一种面向并发的、函数式编程语言,由瑞典...这两本书结合阅读,将为初学者提供一个全面的Erlang学习路径,从基础语法到高级并发编程技巧,有助于深入理解Erlang语言及其在构建高并发、分布式系统中的强大能力。
7. **并发与分布式**:Erlang的VM(Virtual Machine)允许在多核甚至多机器上并行运行,轻松构建分布式系统。它的轻量级进程和网络透明性使得跨节点通信变得简单。 8. **错误处理**:Erlang鼓励使用“失败-快速”...
**Erlang编程语言简介** Erlang是一种高级并发编程语言,由...通过《erlang中文基础教程.doc》文档和《更多erlang资料下载.txt》文件,你可以获取更多的Erlang学习资料和实践案例,逐步掌握这一强大而独特的编程语言。
内容概要:本文档详细介绍了Erlang编程语言及其并行编程模型,并重点阐述了Erlang OTP框架的特性和应用场景。首先,文档简述了Erlang语言的特点,包括轻量级进程、模式匹配和热代码升级等特性,以及它在构建高可用、...
Erlang OTP 19_win64是一款专为Windows 64位系统设计的Erlang软件开发工具包,它包含Erlang编程语言和OTP(Open Telecom Platform)框架。Erlang是一种强大的、动态类型的函数式编程语言,特别适合构建高可用性、...
### Erlang多核编程入门知识点总结 #### 一、Erlang多核编程背景与重要性 - **多核时代的来临**:随着技术的发展,单个芯片内部的...通过学习和掌握Erlang的多核编程技巧,开发者可以更加从容地面对多核时代的挑战。
- **错误处理**:Erlang采用异常处理机制,鼓励编写无副作用的纯函数,有助于编写容错性强的代码。 - **模式匹配**:Erlang的模式匹配功能允许在函数定义中使用模式来匹配和解构数据结构,简化了代码编写。 - **...
Erlang是一种面向并发的、函数式编程语言,特别适合构建高可用性和容错性的分布式系统,如游戏后端。某流水过千W的erlang游戏后端项目,揭示了Erlang在处理大规模并发、实时性以及稳定性方面的强大能力。 1. **并发...
8. **多核心支持**:Erlang运行时系统(ERTS)充分利用多核CPU资源,通过调度器和进程分配策略,确保多处理器环境下的高效运行。 9. **IO处理**:Erlang的IO系统基于Unix哲学,将所有设备视为文件,支持多种IO模型...
**Erlang: 并行计算与云计算** Erlang是一种动态类型的函数式编程语言,由爱立信在1986年为电话交换系统设计,后来因其在处理并发、分布式和容错性上的优秀特性,逐渐在并行计算和云计算领域崭露头角。 ### 1. ...
《Erlang编程语言中文手册:www.erldoc.com深入解析》 Erlang是一种功能强大的并发编程语言,尤其在分布式系统、实时系统以及容错领域有着广泛的...定期更新的内容确保你能紧跟Erlang的最新发展,提升你的编程技能。