“小语言”才是编程的未来!

36664938b972980d6a3cb3830e13fdb6.gif

摘要:随着软件功能不断增加,代码数量也日益膨胀,我们要如何停止不断堆砌,甚至缩小软件体积?本文作者提出了一种可能性:“小语言”。

链接:https://chreke.com/little-languages.html

声明:本文为 CSDN 翻译,未经允许禁止转载。

作者 | Christoffer Ekeroth       

译者 | 弯月   责编 | 郑丽媛

出品 | CSDN(ID:CSDNnews)

我认为,“小语言”——旨在解决非常具体问题的小语言——是编程的未来,尤其是在阅读了 Gabriella Gonzalez 的文章《编程历史的终结》(The end of history for programming),并观看了 Alan Kay 的演讲《编程与扩展》之后,我更加确定了这个看法。

b52eab8b19c5c317c910406c4c4c0bf6.jpeg

5722e092201f521da9edfc6a66634170.png

什么是“小语言”?

“小语言”这个词源自 Jon Bentley 的一篇文章《Little Languages》(小语言),他给出的定义如下:

……小语言指的是专门针对某个特定问题领域的编程语言,不包含传统语言的许多功能。

举个例子,SQL 就是一种描述数据库操作的小语言,正则表达式是一种用于文本匹配的小语言,Dhall 是一种用于配置管理的小语言,等等。

这些语言还有一些其他名称,比如领域特定语言(Domain-specific languages,简称 DSL)、面向问题的语言等等。但是,我最喜欢“小语言”这种叫法,有一部分原因是“DSL”一词包含的含义太多了,包括从具有流式接口的库到成熟的查询语言(如 SQL)。此外,“小语言”这种叫法还强调了这类语言的一个本质:小。

b2fe2320aa77b4c579b17a02bd9b35b6.png

为什么我们需要小语言?

从工程的发展史来看,如今的软件也属于某种工程,但从事这种工程的人并不懂得“拱门”为何物。现在大多数软件与埃及金字塔非常相像,由数百万块砖相互堆叠而成,没有结构完整性,只是靠蛮力和成千上万的奴隶建造的。

—— 艾伦·凯,摘自《与艾伦·凯的对话》

软件工程社区真正遇到的问题是,随着应用程序的复杂性增加,其源代码的规模也会随之增加。然而,我们知道大型代码库的能力在很大程度上仍然是固定的。根据 Sourcegraph 于 2020 年发起的一项调查 The Emergence of Big Code 表明,大多人都表示他们的代码库出现了以下一个或多个问题:

  • 很难添加新员工;

  • 缺乏对依赖关系的理解,导致代码出问题;

  • 代码变更的管理难度越来越大。

更糟糕的是,应用程序正以惊人的速度增长,据 Sourcegraph 调查,大多人认为他们的代码库在过去十年中增长了 100~500 倍。举一个具体的例子,1992 年 Linux 内核刚问世时只有大约 1 万行代码,但在 20 年后的今天已经达到了 3000 万行。

这些代码从何而来?我认为“更多功能”不足以解释这些代码量的增加,相反,我认为这与我们构建软件的方式有关。在程序中添加新功能的常见方法是:在现有功能之上不断堆叠——这不恰恰就是金字塔的搭建方式吗?不同的是,每一层所需要的砖会越来越多。

765af0808013e9bc7257a1259f720ca8.png

逆势而上

问题是,我们真的需要数百万行代码来构建现代操作系统吗?2006 年,Alan Kay 与 STEPS 项目的合作者开始挑战这个假设:

科学的进步需要结合实证研究与理论模型,所以作为科学家,我们的首要问题是,如果我们以个人计算现象为基础建立一个模型,是否可以将其提炼为极度简化的东西,就像适用于所有电磁波谱的麦克斯韦方程组,或者是可以浓缩至衬衫口袋大小的美国宪法?还是说这个模型非常混乱(或者极端复杂),就像美国的法律体系(或当前的软件实践)一样“堆积起来有 3 立方英里”那么高的判例法?答案几乎是肯定的:介于两者之间。果真如此的话,能证明这个模型更接近于简化,而不是极端复杂,那一定非常有趣。

所以,我们的问题是:个人计算体验(将操作系统、应用以及其他支持软件的经验都算在内)本质上指的是多少行代码?20 亿行、2 亿行、2 千万行、2 百万行、20 万行、2 万行还是 2 千行?

—— 《STEPS 2007 年进度报告》,第 4~5 页

这里,Kay 提到的麦克斯韦方程组是一组描述电磁学、光学和电路基础的方程式。这些方程式的使用范围非常广,但方程式本身很紧凑,甚至可以印到 T 恤衫上:

f245bcd58f9570360c3c4c323c8c4de0.png

这些方程式如此简洁的原因之一是,使用了 Del 符号(∇)来描述向量微积分运算。需要注意的一点是,Del 并不是真正的运算符,它更像是一种简写形式,可以方便我们使用向量微积分中的某些方程。

那么,我们可以创建编程界的 Del 符号吗?就像 Del 可以让向量演算更易于管理一样,我们是否可以找到某种符号,以相同的方式帮助我们理解程序?这个问题正是 STEPS 项目背后的核心思路之一:

此外,我们认为创建面向问题的语言可以降低解决问题的难度,可以使解决方案更易于理解且更小,并且也符合我们“主动数学”方法的精神。这些“面向问题的语言”将被创建并用于大大小小的问题,以及不同层次的抽象和细节。

—— 《STEPS 2007 年进度报告》,第 6 页

这里的基本思路是,在寻找应用程序中的模式时,你可以用一种小语言将它们编码,这种语言将允许你以比其他抽象方法更紧凑的方式来表达这些模式。这样不仅可以逆转应用程序不断增长的趋势,而且还可以让代码库在开发的过程中缩小!

我发现,Nile(https://github.com/damelang/nile)是 STEPS 计划的一大成果,这是一种用于描述图形渲染和合成的小语言,目标是使用 Nile 实现与 Cairo 相同水平的功能。Cairo 是各种免费软件项目都在使用的一种开源渲染器,总代码量约为 44,000 行——而 Nile 只有大约 300 行。


76bda3861d5a078b619ced018f8d1f16.png

为什么不是高级语言?

尽管如此,事实证明 Ada 并不是干掉软件生产力怪物的灵丹妙药。毕竟,它也只是一种高级语言,这类语言带来的最大收益来自第一次转变,从机器意外的复杂性上升到更抽象的逐步解决方案。在剔除这些意外后,剩下的意外就会变少,而剔除它们的回报自然也会减少。

—— Frederick P. Brooks,《No Silver Bullet》

说到这里,你可能想问:“为什么我们不能发明一种更高级的通用语言呢?”我认为,通用语言的表达能力带给我们的收益已在递减。那么,更高级的语言将是什么样子呢?以 Python 为例,这门语言如此高级,看起来已经很像伪代码了。

通用语言的问题在于,你仍然需要将问题转化为算法,然后再用语言表达算法。如今的高级语言非常擅长描述算法,但除非你的目标是实现算法,否则它也会意外的复杂。

在写这篇文章的时候,我想起了一个关于 Donald Knuth 的故事:有人让 Knuth 在 Jon Bentley 的 Programming Pearls 专栏中展示他的编程风格,而 Doug McIlroy 应邀对 Knuth 的程序发表评论。

Knuth 的任务是计算某一段文本中的词频,其解决方案是用 WEB 语言精心编写的,这门语言是 Pascal 的变体,也是他自己编写的。Knuth 添加了一个专门用于跟踪字数的数据结构,所有代码不到 10 页。虽然 McIlroy 很快就称赞了 Knuth 的解决方案,但他对程序本身并不是很满意。作为评论的一部分,他用 shell 脚本、Unix 命令和小语言编写了自己的解决方案:

tr -cs A-Za-z '\n' |
tr A-Z a-z |
sort |
uniq -c |
sort -rn |
sed ${1}q

对于不熟悉 Unix 的人来说,这段代码不太容易理解——McIlroy 本人也承认这一点,他甚至添加了一个带注释的版本。但很显然,相比十页的程序,这段代码更容易理解。

Unix 命令是为操作文本而设计的,这就是为什么 McIlroy 可以编写出一个如此紧凑的字数统计程序。或许,我们可以将 shell 脚本视为文本操作的“Del 符号”?


4c071aed1ffd37c25d7c916c291d5c9b.png

少即是多

上述 Unix 命令示例说明了小语言的另一个特征:语言本身不是特别强大,但运行时非常强大。Gonzalez 在文章《编程历史的终结》中提到了如下趋势:

在研究上述趋势时,我们发现了一个共同的模式:将用户关心的某个问题转变成运行时的问题,可以……让使程序更像纯数学表达式,并且……运行时的复杂性明显增加。

正则表达式和 SQL 只能用于表达文本搜索和数据库操作。与之相对的是,C 等没有运行时的语言,你可以表达任何在冯-诺伊曼架构上可能出现的东西。而 Python 和 Haskell 等高级语言介于两者之间:你无需在意内存管理,但仍然可以使用图灵完备语言的全部功能,这意味着你可以表达任何计算。

小语言和 C 语言处于两个极端。对于小语言来说,不仅计算机的体系结构被抽象掉了,其中一些语言可以表达的程序种类也有限制——它们在设计上是不具备图灵完备性的。虽然听上去这些语言非常受限,但实际上它们为优化和静态分析开辟了全新的可能性。而且,就像抽象出内存管理可以消除一大类错误一样,尽可能地抽象出算法也有助于消灭更多的错误。


4329ee0f73baee2b6758693cd2ea92f5.png

静态分析

功能不是十分强大的语言更容易推理,而且可以提供比通用语言更强的保证。例如,Dhall 是一种用于生成配置文件的全功能编程语言,如果你不想冒险让部署脚本崩溃或将它们置于无限循环中,则可以考虑 Dhall,因为它可以保证:

1.不崩溃;

2.在有限的时间内结束。

第一点的实现方式是不抛出异常,任何可能失败的操作(例如获取空列表中的第一个元素)都会返回一个可选的结果,其中可能包含值,也可能不包含。第二,为了保证结束,Dhall 不允许程序使用递归定义。在其他函数式编程语言中,递归是表达循环的主要方式,但在 Dhall 中,你必须依赖内置的 fold 函数。缺少通用的循环结构意味着 Dhall 不是图灵完备的语言,但由于它不是一种通用的编程语言,所以也没有这个必要。

如果语言很小,理解起来就更容易。例如,你很难确认 Python 程序是否有副作用,但对于 SQL 来说却很简单,你只需检查查询是否以 SELECT 开头。

对于 Nile,STEPS 团队看到了对图形调试器的需求。Bret Victor 想出了一个工具,可以告诉你在屏幕上绘制特定像素的代码。你可以通过 YouTube 观看 Alan Kay 的演示,也可以自己动手尝试一下。这样的工具是完全可行的,因为 Nile 是一种易于推理的小型语言——想象一下,如果用 C++ 编写同样的一款工具会是什么样子?


80da9162e57d418ec21bd9184d39751f.png

对速度的要求

强大的编程语言不仅会增加出现 bug 的可能性,还会对性能产生不利影响。例如,一个程序没有用算法来表达,运行时可以自由选择;我们可以用更快的表达式来替换,当然前提是我们能证明它们能产生相同的结果。

例如,SQL 查询并没有规定应该如何执行查询,数据库引擎可以自由使用它认为最合适的任何查询计划,例如应该使用一个索引、多个索引的组合,还是直接扫描整个数据库表。现代数据库引擎还会收集有关列的值分布的统计信息,这样它们就可以即时选择最优的查询计划。如果查询是通过算法的方式描述的,那就不可能了。

Nile 语言如此紧凑的“秘密武器”之一是 Jitblt,这是一种用于图形渲染的即时编译器。从 STEPS 和 Cairo 团队之间的讨论可以清楚地看出,Cairo 的许多代码都是手动优化像素的合成操作,理论上这部分工作可以交给编译器。因此 Cairo 团队的 Dan Amelang 实现了这样的一个编译器,它就是 Jitblt。这意味着,图形流水线的优化工作可以与渲染内容的纯数学描述分离,这也是 Nile 的运行速度与手动优化过的 Cairo 一样快的原因。

9423fb7eb0ceabc762267108e723b04a.png

小语言,大潜力

那么,STEPS 项目最后怎么样了?他们最终得到了“堆积起来有 3 立方英里的判例法”,还是设法创建了一个“可以印到 T 恤衫上的操作系统”?他们的最终结果是 KSWorld,这是一个完整的操作系统,包括文档编辑器和电子表格编辑器,大约有 17000 行代码。虽然无法印到 T 恤衫上,但我仍然认为这个项目是成功的。

KSWorld 的创建表明小语言有很大的潜力。然而,我们还有许多问题没有解决,例如这些小语言之间应该如何互通?它们应该编译成一个通用的中间表示吗?或者使用不同的运行时,然后通过通用协议(例如 UNIX 管道或 TCP/IP)相互通信?或者,也许每种语言足够小,可以用各种不同的宿主语言重新实现(如正则表达式)?亦或者,我们可以结合使用这些方式?

无论怎样,我认为我们需要一种不同的方式来构建软件。小语言能否成为这条发展道路上的一部分,也许我们还没有答案,但重要的是我们必须停止不断堆砌砖头,同时还需要想出一种更好的办法。

43723503b5bb3e06afc84a991f864f38.gif

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/510710.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

夯实密码基础服务,服务上层应用

“十四五”是国家数字化战略转型建设的关键阶段,5G、人工智能、云计算、大数据等新一代信息技术进一步加快了工业和信息化领域数字化转型的步伐。与此同时,也带来了新的网络安全风险。加快推动商用密码与新一代信息技术的深度融合和协同创新,…

储留香:数据迁移上云避坑指南

简介: 常言道:人往高处走,水往四面八方流,而让数据如水一般流动则是IT人孜孜以求的。那么在如今这个风起“云”涌,不管是上云,还是换云都涉及到数据迁移的时代,如何做到这一点呢?今天…

为 Serverless Devs 插上 Terraform 的翅膀,实现企业级多环境部署(下)

在上篇中,主要介绍了 Serverless Devs 多环境功能的使用,用户读完可能会些疑问,本文会就一些常见问题进行下回答。 1、Serverless Devs 和 Terraform 的关系 可能有些用户会问,既然你们已经支持了 Terraform,那 Serv…

这个简单的小功能,半年为我们产研团队省下213个小时

大多数人对产研同学的认知都是每天做着高大上的活儿。 我们以为的产研团队是: 研发负责人:今年最新的技术架构是什么、我的团队适合吗?开发同学:010001,一顿代码猛如虎测试同学:OK,测试一次性…

腾讯云开源项目Crane成FinOps首个认证降本增效开源方案

刚刚,腾讯云开源项目 Crane(Cloud Resource Analytics and Economics)正式成为FinOps认证解决方案(FinOps Certified Solutions)。作为全球范围内首个开源的FinOps认证解决方案,Crane能够助力云原生用户充分发挥云上资源的最大价值…

JDBC 在性能测试中的应用

前言 我们能否绕开 http 协议,直接测试数据库的性能?是否觉得从数据库中导出 CSV 文件来构造压测数据很麻烦?怎样在压测结束后做数据清理?能不能通过数据库中的插入(删除)记录对压测请求做断言&#xff1f…

不喜欢 D 和 C++,程序员将 58000 行代码移植到 Jai 语言?

摘要:将已有的上万行代码迁移至另一种编程语言,从来就不是一件容易决定的事情,而本文作者却信心满满地要将 5.8 万行代码全部用另一种不那么主流的语言重写,这是为什么呢?链接:https://www.yet-another-blo…

传统微服务框架如何无缝过渡到服务网格 ASM

背景 软件技术的发展历史,从单体的应用,逐渐演进到分布式应用, 特别是微服务理念的兴起,让大规模、高并发、低延迟的分布式应用成为可能。云原生时代下,微服务框架本身也在不断地进化和迭代演进。 微服务框架一般会涉…

基于 K8s 的交付难题退退退!

大家好,我是专注于交付的王小锤,看过交付铁三角系列故事(专注交付的我小锤,开发老哥铁子和售前大佬强哥)的同学想必都知道,我们三人服务于一家提供大数据分析服务的 ISV 企业,在应用交付过程中时…

小迈科技 X Hologres:高可用的百亿级广告实时数仓建设

通过本文,我们将会介绍小迈科技如何通过Hologres搭建高可用的实时数仓。 一、业务介绍 小迈科技成立于 2015 年 1 月,是一家致力以数字化领先为优势,实现业务高质量自增长的移动互联网科技公司。始终坚持以用户价值为中心,以数据…

移动云探索自主技术核心地带,拥抱开发者共筑全新技术生态

在数字经济向更多新领域渗透,5G、物联网等数字经济核心技术应用加速的助推下,云计算作为最主流的算力解决方案,需求增长迅速。随着国内云计算技术生态发展的不断成熟,各行各业上云的步伐也在不断加快。同时,由于企业的…

深度解读 RocketMQ 存储机制

RocketMQ 实现了灵活的多分区和多副本机制,有效的避免了集群内单点故障对于整体服务可用性的影响。存储机制和高可用策略是 RocketMQ 稳定性的核心,社区上关于 RocketMQ 目前存储实现的分析与讨论一直是一个热议的话题。本文想从一个不一样的视角&#x…

IOC-golang 的 AOP 原理与应用

AOP 与 IOC 的关系 AOP (面向切面编程)是一种编程设计思想,旨在通过拦截业务过程的切面,实现特定模块化的能力,降低业务逻辑之间的耦合度。这一思路在众多知名项目中都有实践。例如 Spring 的切点 PointCut 、 gRPC的…

达摩院技术创新全景|懂你的语音AI

过去十年,语音AI从实验室走向应用,语音搜索、交互早已融入日常。本文将带你一览达摩院语音AI技术创新全景,一起感受能听、会说、懂你的语音AI。 当你在家中与智能音箱进行交互对话,当你使用天猫超市或菜鸟裹裹,接到机器…

闲鱼对 Flutter-Native 混合工程解耦的探索

1. 闲鱼Flutter现状 闲鱼是第一个使用Flutter混合开发的大型应用,但闲鱼客户端开发最深入体会的痛点就是编译时长影响开发体验。在FlutterNative这种开发模式下,Native编译速度慢,模块开发无法突破。闲鱼集成了集团众多中间件,很…

算法通关第二十关-青铜挑战认识图结构

大家好我是苏麟 , 今天来聊聊图结构 . 我们平时在工作、学习中会大量使用图结构,不过呢在使用代码进行具体实现的时候极少使用图,主要是图里容易产生环,难以处理。 在算法里,考察图也不是很多,主要是图的表示非常复杂&…

我的前端成长之路:中医药大学毕业的业务女前端修炼之路

大家好,我是风月,2014年二进宫进入阿里,目前是业务平台体验技术数据服务前端团队负责人,负责 BizCharts 横向建设以及财鲸数据业务支撑。本次分享我将回顾作为业务前端从前端工程转型到数据可视化过程中的心路历程。 前端工程师的…

过去5年,PolarDB云原生数据库是如何进行性能优化的?

云数据库实现计算存储分离,支持计算与存储的独立扩展,其用户还可以享受按量付费等特性。这使得基于云数据库的系统更加高效、灵活。因此,构建并使用云原生数据库的势头愈演愈烈。另一方面,云化存储服务已经是云的标准能力&#xf…

ChatGPT 玩「脱」了,写了份毁灭人类计划书,还遭到了 Stack Overflow 的封杀.........

【CSDN 编者按】OpenAI 的新通用聊天机器人原型 ChatGPT 可谓是风靡一时,但却突遭 StackOverflow 封禁。整理 | 刘春霖 责编 | 张红月出品 | CSDN(ID:CSDNnews)在上周发布的《挑战 Google 搜索?OpenAI 发布最强 …

基于任务调度的企业级分布式批处理方案

背景 先来谈下什么是分布式批处理,从字面来理解就是有大批量的业务数据需要应用程序去批量计算处理,而通过单机模式去执行会耗费很长的处理时间,也不能充分发挥业务集群中每个应用节点处理能力。通过一些常见的分布式批处理方案,…