OCaml 局部类型:regional 参数与循环区域

原标题OCaml Local Types: Regional Parameters and Loop Regions

一段演示解释为什么某些局部参数能够跨越函数边界,以及循环区域如何回收分配的内存。

频道
Jane Street
发布
2024年6月13日
视频
11:28
阅读
3 分钟
幻灯片
5
原文
英语
在 YouTube 打开
往下滚动阅读时,视频会缩到右下角继续播放。字幕跟随阅读语言。
阅读语言共 2 种语言可读
由 AI 从英语原文翻译。打开“对照原文”可以逐段核对。
摘要

30 秒看懂

一位 Jane Street 讲者继续介绍公司 OCaml 编译器分支中的局部类型。通过恒等函数和迭代函数,本集解释局部参数的隐藏 regional 处理方式、尾调用以及每次迭代的区域。

  1. 1看似逃逸的值虽然规则规定局部值不能逃离其区域,恒等函数仍可以接收并返回局部字符串。
  2. 2隐藏的 regional 模式局部参数由调用者提供,在函数内部是 regional,因此可以逃离一个区域。
  3. 3丢失 regional 信息将 regional 函数传过恒等函数会返回一个 local 值,该值不能传入尾调用。
  4. 4循环周围的区域每个循环体区域都可以在下一次迭代之前回收局部分配的内存。

要点建议

  1. 标记为 local 的参数在函数内部按 regional 处理。
  2. regional 值来自区域外部,因此可以跨越一个区域边界。
  3. 返回这样的值时,调用者看到的是 local 值,而不会保留 regional 信息。
  4. 将 regional 值传过返回 local 值的恒等函数,可能丢失尾调用所需的信息。
  5. 循环体创建的区域允许每次迭代回收局部分配的内存。
全文

按章节阅读整理后的全文

只看原始文稿
01

两个令人意外的例子

局部恒等函数返回其输入,而递归迭代器将局部函数传入尾调用。两者看似都与区域规则冲突。

本集继续介绍 Jane Street 公开提供的 OCaml 编译器分支中的局部值。我将通过看似违反前几集规则的例子,解释区域以及一个名为 regional 的隐藏模式。

考虑一个恒等函数,其参数被标记为局部字符串。它可以通过编译,推断出的类型接收一个局部字符串并返回一个局部字符串。这看起来令人意外:每个函数都定义一个区域,而局部值不应该逃离其区域。

局部恒等函数
幻灯片 1 / 5局部恒等函数推断出的函数类型接收并返回一个局部字符串。

第二个例子是遍历列表的递归迭代器。它接收一个函数,将其应用于每个表头,并对剩余部分进行尾递归调用。把函数参数标记为 local,让调用者可以提供闭包,而不一定要在堆上分配该闭包。

迭代器中的局部函数参数
幻灯片 2 / 5迭代器中的局部函数参数递归列表迭代器接收一个局部函数,并将它传入尾调用。

虽然递归调用是尾调用,位于当前函数区域之外,迭代器仍然能够通过编译。为什么函数参数可以传到那里?恒等函数的返回和迭代器的尾调用似乎都允许局部值逃逸。

02

regional 模式

局部参数在函数内部按 regional 处理,可以跨越一个区域边界。将它传过返回局部值的函数会丢失这一信息。

原因是标记为 local 的参数在函数内部按 regional 处理。regional 是隐藏模式,不是可以写在程序中的关键字。regional 值可以逃离一个区域,但也可以完全不逃离。

局部参数是 regional
幻灯片 3 / 5局部参数是 regional代码注释标出了参数在函数内部使用的隐藏模式。

参数一定由调用者提供,因此它的生命周期已经超出被调用函数自己的区域。允许它跨越这一个边界是安全的。在恒等函数示例中,返回的字符串对调用者而言是 local:它不能直接成为 global,否则真正的局部值就可能逃得太远。

在迭代器中,函数参数在当前调用内部也是 regional。因此,尽管当前函数的区域在尾调用之前结束,它仍可以跨过该边界,传给下一次调用。

为了展示区别,我将迭代器的函数参数传过一个恒等函数,其类型接收并返回局部值。我们只知道结果是 local;类型没有保留原参数是 regional 的信息。此时将结果传给尾调用就会产生局部值逃逸错误。

经过恒等函数后丢失 regional 信息
幻灯片 4 / 5经过恒等函数后丢失 regional 信息编译器拒绝将局部结果传给尾调用。
03

循环体中的区域

讲者将迭代器改写为数组循环。每次迭代的区域决定局部分配的内存何时可以回收。

循环体周围也有区域。我将迭代器改写为用 for 循环遍历数组,对每个元素调用函数。这个例子关注循环运行时局部分配的生命周期。

如果被调用函数返回局部值,其局部分配发生在父区域中,本例中就是循环体区域。每次迭代结束时,该区域都可以在下一次迭代之前回收。没有这样的边界,重复工作可能在循环中不断累积空间。

循环体区域
幻灯片 5 / 5循环体区域数组迭代器在循环中调用一个返回局部值的函数。

讲者指出,在这个示例中,循环规则对类型检查的影响较小,因为循环通常不会返回值,除非通过引用等机制。但它仍有助于理解内存分配行为:循环区域中的局部分配会随着本次迭代结束而结束。

同频道的其他文章

6 张幻灯片15:33EN → 简体中文
JSJane Street· 2026年10月26日Figgie 策略:解读手牌、争夺多数与定价Bradley, Mike · Jane StreetJane Street 交易员 Bradley 和 Mike 分析三局游戏,展示私人信息、市场竞争和时机如何影响牌价。Decision MakingMathematicsFintech
1:48:29EN → 简体中文
JSJane Street· 2026年10月16日AI 如何改变编程:John Krazit 与 Ron Minsky 的对话Ron Minsky, John Krazit · Jane StreetJane Street 的 AI 工具负责人和 Signals and Threads 主持人探讨智能体基础设施、安全、代码审查,以及软件开发体验的变化。编程智能体Developer productivity评估+2
1:36:37EN → 简体中文
JSJane Street· 2026年9月23日Aaron Bauer:在 AI 时代教授软件工程Ron Minsky, Aaron Bauer · Jane Street当模型能够生成代码时,学习目标、主动练习和编辑器设计如何影响工程教育。AI in EducationSoftware engineeringEducation+2
9 张幻灯片1:05:45EN → 简体中文
JSJane Street· 2026年9月11日Cyrus Omar:实时编程与人与 AI 共享的计算公共空间Cyrus Omar通过 Hazel 演示,探讨即时反馈、结构化协作和精细权限如何帮助人类与 AI 智能体共同工作。Programming LanguagesHuman-AI Collaboration开发流程与测试+2
1:25:00EN → 简体中文
JSJane Street· 2026年9月2日Eric Mannes:如何将杂乱的外部数据用于交易研究Ron, Eric Mannes · Jane Street从商品期货和 Excel 风险系统,到时点数据集和 AI,Eric Mannes 解释 Jane Street 数据工程背后的领域知识。Data quality & curation开发流程与测试Investing+2
7 张幻灯片1:16:29EN → 简体中文
JSJane Street· 2026年8月26日Grant Sanderson 与 Alok Puranik:从群论看位置编码Grant Sanderson, Alok Puranik · 3Blue1Brown从注意力机制的假设出发,他们推导矩阵指数,并将旋转、衰减和 Jordan 块与 RoPE、ALiBi 联系起来。Transformers & attentionMathematics机器学习基础+1