性能为何如此重要(以 Python 和 Rust 为例)
长篇引言
我在 dev.to 上的第一篇正式帖子发表于 2017 年 9 月,内容如下:
我当时尝试从大约 60 GB 的 CSV 文件中提取信息,这些文件对应 1.39 亿个事件。我先用 Python 测试了一下,看看它的表现如何。这次实验的起因是我对 Redshift 的不满,以及我想尝试一下TrailDB这个用于查询事件序列的库。我的测试并不严谨,但切换到 Go 之后(当时我对这门语言并不熟悉,所以只能复制粘贴代码),我成功地将数据库搭建速度提升了 2.6 倍(比 Python 快 2.6 倍),数据查询速度也提升了 2.54 倍。
速度和性能这个话题可能对本网站上的每个人来说都很重要,即使速度和性能会因具体情况而异(参见“足够快”的概念)。在 dev.to 论坛上,关于网页加载速度慢、浏览器和桌面应用程序的内存占用以及其他相关话题的讨论中,都贯穿着这个主题。以下是一些不错的例子,以及相关的深入讨论:
作者:@quii
文章已失效
作者:@tux0r
你为什么会在这里阅读这篇文章
没有人会反对经济高效的速度提升,而这正是本文的重点。一篇题为《使用 Rust 将日志解析速度提升 230 倍》的文章引起了我的注意,作者是 André Arko(Ruby Bundler的主要开发者)。
我早就注意到Rust的速度了……嗯,还有它在内存管理方面的优势,这也是大家谈论Rust时最常提到的:-D
我已经改用两个基于 Rust 的工具,每天在命令行中使用:bat代替了cat,尤其是ripgrep代替了grep和ack。速度提升非常明显(感谢@dmfay的建议)!
回到文章正文。Arko 想查询 Bundler每天 500 GB 的海量日志,从中提取有关社区的有用信息。每个日志文件都包含数百万条 JSON 格式的事件(顺便说一句:如果可以,请使用结构化日志,例如 JSON 或键值对,以后你会感谢我的)。目前,这些文件以压缩格式存储在 S3 存储桶中,每月只需几美元。
托管式日志记录解决方案太贵了,所以他尝试自己想办法实现。
第一次尝试是用 Ruby 语言,结果处理一天的数据竟然花了 16 个小时,简直不可思议。不行。
第二次尝试是用 Python,借助 AWS Glue 和亚马逊服务器的全部性能。他用 100 个并行工作进程,每月花费 1000 美元,将处理时间缩短到 3 小时,平均每个日志文件(共 500 个)的处理时间为 36 分钟。不行。
第三次尝试是用 Rust 语言。他最初将每个文件的解析时间缩短到 3 分钟,然后缩短到 60 秒。经过进一步的调整并收到读者的反馈后,他成功地在 8 秒内解析了一个文件(!!)。
第四次尝试他仍然使用 Rust 语言,并且采用了并行化。速度比顺序执行快了 3.3 倍。这就是标题中提到的 230 倍乘数的由来。
关于比较的几点说明
仔细阅读后,你会发现以下几点:
- 第一次尝试可能不应该在帖子中提及,因为它收集的数据比其他尝试少(而且我们不知道少多少)。
- 首次使用 Rust 进行的尝试,如果按顺序运行,耗时 8.33 小时,比使用 Python 和 Glue 进行的实验快 30 多倍。
- Rust 的最后一个“顺序”实验处理整个 500 GB 数据集仅需 1 个多小时,速度提升非常显著。
部署时间
André Arko 最后谈到的是他如何部署 Rust 脚本,使其能够处理存储在 AWS 上的生产日志。这部分内容让我笑出了声:
我发现了 rust-aws-lambda,这是一个可以让你的 Rust 程序伪装成 Go 二进制文件并在 AWS Lambda 上运行的 crate。
以二进制文件形式分发应用程序的另一个奇妙之处 :D
在 AWS Lambda 上,他获得的速度提升是最初 Python 示例的 78 倍,相当不错!
他做了一些计算,结果显示它完全在 AWS Lambda 的免费套餐范围内。
所以,他通过用 Rust 重写脚本,从每月 1000 美元变成了每月 0 美元。
我查看了脚本的仓库,发现已经有人在提出让它运行得更快的方法了😂
如果你读到这里,可以思考以下几点。
- 提高效率可以帮你省下很多钱。
- 掌握(或愿意学习)多种语言是个好主意
- 对于这类解析任务,Rust 绝对值得考虑。
- 有时候,更好比足够好更好。