从 Python 到 Go 再到 Rust,谁是后端开发之王?

李肖遥

共 3323字,需浏览 7分钟

 ·

2021-08-09 21:30

关注、星标公众号,直达精彩内容

来源:csdn

【CSDN 编者按】作为一种简单易上手的面向对象的动态类型语言,Python 在近两年的技术圈中,可谓是炙手可热;而另一种素有 Google “亲儿子”之称的 Go 语言,被设计成一门应用于搭载 Web 服务器,存储集群或类似用途的巨型中央服务器的系统编程语言,其自从诞生起,就备受业界关注;最后来自 Mozilla 开发的系统编程语言 Rust,在安全性上表现尤为突出,且在过去三年间连续获得了 StackOverflow 开发者调查中“最受喜爱编程语言”的 Top 1。  

在此,如果这三种语言同置于后端开发之中时,将会为开发者带来什么样的体验?而谁又会更胜一筹?

作者 | allomedia

译者 | 弯月,责编 | 屠敏

出品 | CSDN(ID:CSDNnews)

以下为译文:

说起后端语言,我很自然地从Python切换到了程序员们的新宠:Go,但仅一个星期之后,我意识到换成Go只是此次旅行的一半路程。尽管Go比Python更能满足我的需要,但远远比不上我期待中的开发体验,就像我在前端使用Elm时的体验。所以我尝试了一下Rust。

离开Python


在过去三年的后台开发中,我主要使用Python 3。从管理员脚本开始,后来开始写机器学习脚本,到Flask/Django应用程序,我最近大部分时间都在使用Python,但总觉得它不是那么舒服。说实话,我并不是从某个“完全随机的时间点”开始感觉不对劲,而是因为我喜爱上了Elm这个强类型语言。

我很喜欢一句名言:“能通过编译就能用”,一旦你体会到了这一点,就再也回不到过去了。你可以尽情尝试,只要按照编译器给出的友好错误信息改代码,然后就能神奇地使用了!

我开始意识到,我希望的“最佳”后端语言应该拥有以下特性:

  1. 静态类型,强类型

  2. 大多数检查在编译时进行(而且,没有异常!)

  3. 没有null

  4. 没有可修改性

  5. 能漂亮地处理并发

我知道你会说:“嗨,这不就是Haskell嘛!”是的,没错,但不知出于什么原因,我从未能用Haskell完成过什么东西(尽管我尝试了许多)。也许只有我这样吧,但从一个外行的角度来看,Haskell的思维方式过于精英化,也没有太多文档和示例,所以很难入门。《学习Haskell做正确的事情》这本书当然很好,但它太长了,而且对于我来说过于抽象(整本书没有构建任何实际的东西)。

“嘿,那Scala怎么样?”Scala是什么?更好的Java?还是Scalaz的函数式编程语言?还是那个需要4GB JVM才能运行,而且不确定是否会在java.lang.NullPointerException上出现运行时错误的那个面向对象的函数式编程语言?我在几年前尝试过,显然,它并不适合我。

在与一些人讨论之后,我决定试试Go语言。它有编译器,没有异常,没有null(但有null值),而且能很好地处理并发。

尝试Go


我决定用Go语言重写一个用Python写的内部项目,目的只是为了感受两者之间的差异。

第一感觉:学习Go非常容易。我只花了一个晚上,就编译出了该项目的原型版本,实现了最基本的功能,还写了一些测试。能够快速添加功能的感觉非常好。编译器的错误信息也非常有用 ,一切都很好。

结果痛苦开始了。我需要在某个结构体中添加一些字段,于是我修改了结构体,正要打算根据编译器错误找出这个结构体在哪儿用过的时候……

我编译了代码,结果……没有错误信息。一切正常。嗯?但我在结构体中添加了字段啊,编译器应该指出我的代码有错误,因为这些字段并没有初始化!

问题在于,Go语言认为不给结构体提供值是正常的。值的默认初始值就是零,能通过一切编译。这一点我坚决不能接受。我认为,编译器不能在我犯错误的时候替我收拾残局。于是我想:如果Go的编译器并不比Python和mypy更好,那我为什么要学Go语言呢?当然Go语言的并发处理要好得多,但无法依赖编译器的缺点对于我来说太严重了。

不要误会,我依然认为Go能与Python并驾齐驱,如果有人要从两者中选择一个,我依然会推荐学习Go而不是Python。但就我个人而言,我已经学会了Python,只是想要一些更安全的东西,Go并没有给我足够的理由去学习。

尝试Rust


所以,我不会再考虑Go语言,因为我发现我真正想要的是更有帮助的编译器,这个编译器不应该默认我懂得如何编程(大量事实证明我的确不懂)。正因为如此,我开始尝试Rust。

Rust并不是我的第一选择,因为它标榜自己为“系统语言”,而我本身更倾向于Web开发,而不是系统开发。但它有许多非常好的卖点:

  • 没有null值,二是提供了Option类型(编译时检查)

  • 没有异常,但提供了Result类型(编译时检查)

  • 变量默认是不可修改的

  • 设计时考虑了并发

  • 设计时考虑了内存安全,不使用垃圾回收器

我决定重写之前用Python和Go写过的那个项目。Rust入门比Go语言难多了。像Go一样,我试着上手写代码,但发现非常困难:我需要理解许多Rust特有的概念,比如ownership、lifetimes,才能理解我在StackOverflow上看到的代码。所以我只好去阅读《Rust Book》,花了两个星期才能写出一点代码(别忘了Go语言我只花了一个晚上就能写代码了)。

但度过了初期陡峭的学习曲线之后,编写Rust代码变成了一种享受,我现在依然很喜欢编写Rust代码。有了Rust,我不再需要相信自己,只要跟着编译器的指示即可,只要代码能通过编译,那基本上就能用。这正是我一直在寻找的编程感觉。

当然,Rust也有许多缺点:

  • 它非常新,一切发展都很迅速。我的项目中使用了futures-rs和hyper.rs,想找一份好的文档非常困难(感谢irc.mozilla.org#rust-beginners的人提供的帮助)。

  • 它会强迫你思考在使用高阶语言时从未思考过的问题:内存管理(包括lifetimes和ownership的概念)。

  • 编译器的消息有时并不是太容易懂,特别是将futures和它们超长的类型结合在一起时。

  • 可修改性是允许的,所以有时候副作用会让你抓狂。

但是,它也有许多优点:

  • 非常快

  • 工具链非常好(cargo,rustfmt)

  • 大多数东西都在编译时检查

  • 你几乎可以用它做任何事,可以编写浏览器,编写Web应用,甚至还能编写游戏。

  • 社区非常友好

  • 由Mozilla支持

总结


Go语言非常酷,但并没有为我提供足够的类型安全。如果不需要并发,那么我宁可继续使用Python及其生态环境,而不会去冒险采用Go重写一切。如果需要并发,那我也不会使用Go,因为它缺乏类型安全,这个炸弹肯定会爆炸。

Rust非常适合并发和安全,尽管futures-rs的“箱子”(Rust里函数库叫做“箱子”)依然非常新。我认为,以后Rust会成为许多后台的默认语言。

关于Go和Rust更深入的区别的文章和讨论,可以参考Ralph Caraveo(@deckarep)的这篇文章:为Go开发者准备的Rust编程范式(https://medium.com/@deckarep/paradigms-of-rust-for-the-go-developer-210f67cd6a29)。

至少,我认为Rust是我最喜欢的后台语言。

原文:https://tech.allo-media.net/point/of/view/2018/03/22/from-python-to-go-to-rust.html

本文为 CSDN 翻译,转载请注明来源出处。

‧‧‧‧‧‧‧‧‧‧‧‧‧‧‧‧  END  ‧‧‧‧‧‧‧‧‧‧‧‧‧‧‧‧

关注我的微信公众号,回复“加群”按规则加入技术交流群。

欢迎关注我的视频号:


点击“阅读原文”查看更多分享,欢迎点分享、收藏、点赞、在看。

浏览 11
点赞
评论
收藏
分享

手机扫一扫分享

分享
举报
评论
图片
表情
推荐
点赞
评论
收藏
分享

手机扫一扫分享

分享
举报