静态类型与铲子(2026)
摘要
作者认为,2010年代静态类型编程的复兴归功于改进的类型系统(例如 TypeScript、Haskell、Rust),这些系统提供了可空类型处理、和类型以及类型推断,与 Java 和 C++98 等早期语言中糟糕的静态类型形成对比。
<p><a href="https://lobste.rs/s/eiknm1/static_types_shovels_2026">评论</a></p>
查看缓存全文
缓存时间: 2026/06/10 19:49
# 静态类型与铲子
来源:https://carefully.understood.systems/blog-2026-06-10-static-type-shovel.html
首页 (https://carefully.understood.systems/)
简历 (https://carefully.understood.systems/cv.html)
博客文章 (https://carefully.understood.systems/blog_list.html)
[联系](mailto:[email protected])
上一篇:连接池必须传递连接错误 (https://carefully.understood.systems/blog-2026-06-05-connectionpools.html)
我有一个简单的理论,解释为什么静态类型在2000年代到2010年代初变得不那么流行,而在2010年代中期到后期又开始重新流行。这并不是因为编程是一个受时尚驱动的行业,而是因为广泛可用的静态类型系统的质量提高了。打个比方:你想挖一个坑,你是用铲子还是用手?如果铲子好用,你显然会用铲子。但如果唯一可用的铲子是纸做的呢?你只会用它徒劳地在地上挥舞,还不如直接用手挖。
使用动态类型系统时,你需要自己动脑来思考程序中变量和字段的状态与内容。计算机既不帮你也不碍你事,这就像用手挖坑。而如果你得到的静态类型系统很差劲,比如90年代和00年代早期流行的那些——像早期Java或C++98——就相当于一个纸做的铲子。这些静态类型系统连区分可空指针与不可空指针这种简单的事情都做不到。它们没有和类型(sum types),只有积类型(product types)。同时,它们还需要你花大量精力手动到处写类型名称。
`BufferedReader bufferedReader = new BufferedReader(new FileReader(filename));` 就是一个小灾难。
另一方面,如果你得到的静态类型系统很差劲,比如90年代和00年代早期流行的那些,像早期Java或C++98,就相当于递给你一个纸铲子。这些静态类型系统带来了高昂的代价,却连简单的事情都帮不上忙。它们不区分可空指针与不可空指针。它们没有和类型(也称标记联合或判别联合),只有积类型(如结构体)。同时,它们要求你花费大量精力手动到处写类型名称。像下面这样写代码就是浪费脑力和精力:
`BufferedReader bf = new BufferedReader(new FileReader("input.txt"));`
而一个好的类型系统会为你推断出大多数变量类型。
如果你把这种类型系统和现代类型系统(比如TypeScript、Haskell、MyPy、Swift或Rust中的)进行对比,你会发现总是具备以下特点:
- 有某种方式区分可空类型与不可空类型。Haskell 有 `Maybe t`。TypeScript 有 `T | null`。Swift 有 `T?`。Rust 有 `Optional`。类型系统可以轻松地告诉你所有需要进行空检查的位置,以及你是否遗漏了某个检查。在实践中,你几乎不会在运行时看到空指针错误。
- 至少包含和类型或联合类型中的一种,这让你可以遵循“让无效状态不可表示 (https://blog.janestreet.com/effective-ml-revisited/)”的实践。这意味着你可以拥有表示状态机的对象,它们有多个字段,每个字段只在系统处于相关状态时才存在。
- 某种类型推断。我们不需要写 `let x: number = 5;`,编译器可以直接推断出 `let x = 5;` 肯定是一个数字。
另一个让静态类型系统变得更加有用的因素是,IDE特性(比如方法名补全)已经变得更加普及。在90年代,Intellisense 是 Visual Studio 的一个杀手级功能,而到了21世纪20年代,类似的特性几乎在每个IDE和编辑器中都可用。因此,你放入静态类型系统的信息会带来额外的生产力提升,这完全超出了它对程序错误检查的用处。
总结一下:
- 好的动态类型系统胜过差的静态类型系统。
- 但如今我们拥有的静态类型系统比以前好太多了。
© 版权所有 2026 Richard Barrell
相似文章
为什么 AI 智能体几乎都用 TypeScript 编写?
本文探讨了为何 TypeScript 已成为构建 AI 智能体及智能体框架的主流语言,并追问为何 Rust 或 C++ 等替代方案没有得到更广泛的应用。
新Blub悖论,或者说:为什么TypeScript在AI时代是一个糟糕的选择
认为TypeScript由于不健全的类型系统而成为AI时代的一个糟糕默认选项,它无法捕获AI生成的代码中的错误,并将其比作Paul Graham的Blub悖论。
关于整数的思考 (2023)
一篇博客文章,讨论了各种编程语言中整数类型的设计,认为 Rust 强制要求显式指定大小和符号的做法优于那些有默认 `int` 类型的语言。
Rust 项目目标:不可移动类型与保证析构函数
Rust 项目目标概述了不可移动类型和保证析构函数的计划,以提升语言安全性和资源管理。
引用 Mitchell Hashimoto
Mitchell Hashimoto 评论编程语言日益增强的可替代性,以 Bun 从 Zig 重写为 Rust 为例,表明语言已不再是锁定效应的来源。