writing-for-readerslisted
Install: claude install-skill AntheaLaffy/the-missing-semester-skills
# 写给读者的单向沟通
读者是没有你当前上下文的人:后来的队友、接手的维护者、半年后的你。一个优秀软件工程师大约一半功力在写代码,另一半在与他人沟通——本 skill 管「写给别人读」的那一半。这类写作只回答一个主线问题——**为什么**(why),而不是做了什么(what)。做了什么看代码和 diff 就懂;为什么才是来之不易、最容易随时间流失的知识。这条主线叫 **why-not-what**:`code-review` 与 `contributing-upstream` 在交接点都引用这里的契约。
## 操作契约
- **先问,不猜。** 写 commit、注释或 README 前,若不知道改动背后的动机、取舍与遗留问题,先向用户补齐上下文。commit 场景必问四件事:① 什么问题或约束迫使这次改动?② 考虑过哪些备选方案、为何选这个?③ 取舍与影响是什么?④ 有哪些读者会意外的点?用户答不上来就标注「作者未说明」,绝不编造动机。
- **详略与复杂度匹配。** 一行错别字只需要主题行;修一个排查数小时的竞态条件,值得用段落解释问题与解法。显而易见的段落可以省略(改一个 off-by-one,就没有「备选方案」可写);但再平凡的改动,也别只剩一句「fix foo」——零信息量的提交等于没写。
- **克制,尊重读者。** 读者面对太多文字时,一个字都不会读;写作前自问:如果我是读者,我会读吗?解释为什么,相信读者会为自己的情境推出怎么做。用 LLM 生成时尤其要约束它——LLM 擅长批量产出文字,务必要求「精炼的总结,不是长文」。
- **提交拆得语义清晰**(`git add -p`):一个提交 = 一个可独立理解、独立评审的连贯改动。重构不与新功能混提,无关 bug 修复不塞进同一个提交。LLM 也可以帮你把大 diff 按语义切成多个提交,但切完要自己检查一遍。
- **复杂改动升级盘问。** 背景盘根错节时,改用 `/grilling` 逐轮深挖上下文,而不是让用户一次讲完。
## 注释:写代码本身表达不了的内容
好注释解释「为何这样做」,而不是「如何工作」——代码已经展示了过程。值得写的注释类型:
- **TODO**:留足上下文——还缺什么、为什么延期。写在代码里而不是只放 issue tracker,好处是后来者可以直接 grep 到。「TODO: optimize」毫无价值;「TODO: 这段 O(n²) 循环在 n<100 时没问题,规模放大后需要索引」可行。
- **参考资料**:实现论文算法、借鉴外部代码或遵循文档规定行为时,给永久链接,并注明与参考实现的差异。
- **正确性说明**:解释为什么不寻常的代码能产生正确结果。代码展示步骤,注释说明步骤为何奏效。
- **血泪教训**:花了 30 分钟以上才调通、修复方式不明显——记下来。过去的你不知道需要这一步,未来读者也不会知道。
- **常数的理由**:魔法数字也要解释。为什么是 1492?随手选的、测试得出的还是正确性所需?即便「随意选的」也是有用信息。
- **承重细节**:正确性依赖某个看似无关的实现细节(如「必须是 BTreeSet,因为下面迭代顺序有要求」)——务必点出来。
- **「为什么不用」**:刻意避开显而易见的做法时说明理由。典型场景:这里本该用标准库的 hash map,却用了别的结构——不写清楚,某位聪明工程师会把它「修」回标准库,然后重走你踩过的坑。
复述代码的注释是噪音,甚至误导读者——不写。
## README:像漏斗