把 Nix 的属性路径变成《超级马里奥 3》的按键序列
来源:fzakaria.com — 2026-08-05
📋 概述
Farid Zakaria 利用 Nix 语言的惰性求值,把属性路径当作《超级马里奥兄弟 3》的按键序列来驱动一个 NES 模拟器:树上的每个节点是游戏的一帧,每个孩子是一次按键。每一次按键都是一个独立的 derivation,其输入是上一帧的存档,因此 Nix store 变成了模拟器的存档历史,支持对路径任意分支复用。
🔑 核心要点
- Nix 惰性求值的核心是只求值你访问的属性,甚至允许无限递归的属性集合。这意味着数据结构可以按需"按路径取用",用不到的部分根本不会被求值,为后面把游戏状态摊成属性路径提供了基础。
- 把属性路径当作输入,每个节点是游戏帧、每个孩子是按键,state 天然递归。说明游戏树与 Nix 的属性树在结构上完美对应,一条路径就代表一串连续的按键序列,映射非常自然。
- 每次按键是独立 derivation,输入上一帧存档,store 就成了模拟器的存档历史。好处是每个中间帧都被 Nix store 缓存下来,如同自动保存的读档点,随时可回放或继续。
- 在中段一百次按键中分支只多算一次按键,尾部追加也只需一次,前缀可整体复用。这说明想探索不同路线时无需从头重跑,公共前缀对应的帧全部复用缓存,改动成本极小。
- .play 只是把各帧的符号链接目录交给 ffmpeg 拼接,全程不再重跑模拟。好处是生成视频只做一次轻量的文件拼接,已算出的帧都不会浪费,出片高效。
- 属性路径是单个 argv,Linux 限制单参数 131KB,约21,845 次按键封顶,可改为从文件读入以突破。这意味着当前实现受操作系统参数长度上限约束,属于可绕过的工程边界,而非原理层面的限制。
💡 金句
惰性意味着属性路径其实是一段程序:求值器边走边生成它需要的任何东西。
👍 0
👎 0
← 返回 Lobsters 首页