一位开发者对 AI 辅助编写的原始代码行数应用缩减系数,并与历史程序员生产力基准进行比较。
AI translation, not an official translation. Refer to the original for technical details.
Adapted from @garrytan# 关于 LOC 争议 或:当我提到自己近期交付的代码行数时发生了什么,以及这些数字究竟说明了什么。 批评是有道理的。LOC 是一个糟糕的指标。每一位资深工程师都知道这一点。Dijkstra 早在 1988 年就写道,代码行数不应被视为"产出的行数",而应视为"花费的行数"(《论真正教授计算机科学的残酷性》,EWD1036)。(https://www.cs.utexas.edu/~EWD/transcriptions/EWD10xx/EWD1036.html) 那句广为流传的话(通常被归于 Bill Gates,但出处并不明确)说得更为生动:以代码行数衡量编程进度,就像以重量衡量飞机制造进度一样。如果你用代码行数来衡量程序员的生产力,你量错了东西。这个道理四十年前是真理,今天依然是真理。 我发帖说,在过去 60 天里,我交付了 60 万行生产代码。评论迅速涌来: - "那不过是 AI 堆出来的垃圾。" - "LOC 是个没有意义的指标。过去 40 年每一位资深工程师都这么说过。" - "你当然能产出 60 万行。你有 AI 在写样板代码。" - "行数越多是坏事,不是好事。" - "你把数量和生产力混为一谈了。典型的 PM 思维。" - "你的错误率呢?你的 DAU 呢?你的回滚次数呢?" - "这太丢人了。" 其中一些批评是对的。下面是当你认真对待这些批评中最有分量的部分、并且无论如何都把数学算出来时会发生的事情。 ## AI 编程批评的三个分支 它们常常被混为一谈,但实际上是三个不同的论点。 **分支一:LOC 无法衡量质量。** 正确。一向如此。一个 50 行、结构清晰的库,远胜于一个 5000 行臃肿的库。这在 AI 出现之前就是事实,现在依然是事实。这从来都不是一个致命的论点,只是在提醒人们思考自己在衡量什么。 **分支二:AI 会膨胀 LOC。** 正确。LLM 默认会生成冗长的代码——更多样板、更多防御性检查、更多注释、更多测试。即使"实际完成的工作量"没有增加,原始行数也会上升。 **分支三:因此,吹嘘 LOC 是可耻的。** 这里才是论点脱轨的地方。 分支二才是有趣的部分。如果原始 LOC 因某个系数而被膨胀,那么诚实的做法是算出这个缩减系数,然后报告缩减后的数字。这正是本文所做的事情。 ## 数学计算 我写了一个脚本(https://github.com/garrytan/gstack/blob/main/scripts/garry-output-comparison.ts),用于枚举我在 GitHub 上 garrytan/* 名下所有 41 个代码仓库(15 个公开,26 个私有)中,在 2013 年和 2026 年所有由我提交的 commit。对于每一个 commit,脚本统计新增的逻辑行数(排除空行和注释行)。2013 年的语料库包括 Bookface——我那年为 YC 内部构建的社交网络。 2013 年是完整的一年。2026 年截至撰写本文时(4 月 18 日)为第 108 天。 "每天 14 行?太可悲了。" 确实如此。这正是重点所在。 2013 年,我是 YC 合伙人,同时也是 Posterous 的联合创始人,利用夜间和周末写代码。每天 14 个逻辑行,是我在正职工作之余兼职的实际产出。历史研究表明,专职程序员的生产力因项目规模和研究方法不同而差异很大: - Fred Brooks 在《人月神话》中援引了系统编程约每天 10 行的数据(基于 OS/360 的观测); - Capers Jones 在对数千个项目的测量中,得出大约每天 16 至 38 行的结论; - Steve McConnell 的《代码大全》报告,小型项目(1 万行代码)每天产出 20 至 125 行,大型项目(1000 万行代码)则降至每天 1.5 至 25 行——这是一个与规模相关的数字,并非单一定值。 我的2013年基准线并非刻意挑选的。对于一个有正职工作的兼职程序员来说,这很正常。如果你认为正确的基准是50(高出3.5倍),那么2026年的倍数将从810倍降至228倍。依然很高。 ## 两次缩减 对"原始代码行数毫无意义"这一批评,标准的回应是使用逻辑源代码行数(SLOC,即源代码行数,不含注释和空行)。cloc和scc这类工具20年来一直在计算这个指标。相同的代码,去掉冗余内容:没有空行,没有单行注释,没有注释块正文,没有行尾空白。 但逻辑SLOC并不能完全消除AI带来的膨胀。AI会在高级工程师一行不写的地方写出2到3个防御性的null检查。AI会在根本不会抛出异常的地方内联try/catch。AI会把`return foo()`拆写成`const result = foo(); return result`。 所以我们来进行第二次缩减。假设AI生成的代码在逻辑层面比高级工程师手写的代码冗余2倍。这已经是很激进的假设了——我见过的大多数测量数据显示倍数在1.3到1.8之间——但这是持怀疑态度的人所要求的上限。 - 我2026年每日NCLOC产出:11,417行 - 经2倍AI冗余缩减后:每天5,708逻辑行 - 经两次缩减后的日产量倍数:408倍 现在选择你的预设: - 5倍缩减(没有依据,但姑且算上):162倍 - 10倍缩减(病态假设):81倍 - 100倍缩减(不可能——那相当于每分钟持续产出一行):8倍 关于系数大小的争论并不能改变结论。无论如何,这个数字都是巨大的。 ## 每周分布情况 "你的每日数据假设产出均匀。展示一下分布情况。如果只是某次集中爆发,你的运行速率就是虚假的。" 有道理。 但这并非某次峰值突破。这个速率一直大致稳定,并略有上升。自己运行脚本验证一下吧。 ## 质量问题 这是最有价值的批评,借Sentry创始人David Cramer之口提出:好,你在推送更多代码行。那你的错误率在哪里?合并后的回滚记录呢?你的缺陷密度如何?如果你打字速度提升了10倍,但提交的缺陷增加了20倍,那你不是在提升杠杆,而是在规模化地制造噪音。(https://x.com/zeeg) 有道理。以下是数据: **回滚情况。** 对15个活跃仓库执行`git log --grep="^revert" --grep="^Revert" -i`:351次提交中有7次回滚,回滚率为2.0%。作为参考,成熟的开源代码库通常在1%到3%之间。对你认为是标准的代码库运行同样的命令,然后比较。 **合并后修复情况。** 匹配`^fix:`且引用同一分支上前一次提交的提交记录:351次中有22次,占6.3%。这是健康的修复周期。零修复率只会意味着我没有发现自己的错误。 **测试。** 这才是真正重要的事,也是彻底改变我工作方式的事。2026年初,我在没有测试的情况下发布代码,结果被bug淹没。后来我达到了30%的测试代码比,再后来在关键路径上实现了100%覆盖率,突然之间我就可以飞速前进了。测试用例从1月份所有仓库中的约100个增长到现在的2,000多个。它们在CI中运行,能够捕获回归问题。每个gstack的PR正文中都有覆盖率审计。 真正的洞见在于:多层次的测试才是让AI辅助编程真正奏效的关键。单元测试、端到端测试、以LLM为评判者的评估、冒烟测试、劣质代码扫描。没有这些层次,你不过是在高速生成充满自信的垃圾代码。有了它们,你就拥有了一个验证循环,让AI能够不断迭代,直到代码真正正确为止。 gstack 的核心真实代码特性——那个不只是 markdown 提示词的东西——是我专门编写的一个基于 Playwright 的 CLI 浏览器,这样我就能不再手动对我的东西进行黑盒测试。 /qa 会打开一个真实的浏览器,导航到你的 staging URL,并运行自动化检查。这是 2,000 多行真实的系统代码(服务器、CDP 检查器、快照引擎、内容安全、cookie 管理),它的存在是因为测试是解锁生产力的关键,而不是额外的负担。 /pair-agent 是我为自己做的一个非常有趣的功能,这样我的 OpenClaw 就可以在我真实桌面的 Chromium 浏览器上冲浪和帮我做事,而我可以在一旁观看。它给你一个 MCP bearer token,并建立一条 ngrok/tailscale 隧道,让你的远程代理能够执行 GStack /browse 所能做的一切。 **Slop 扫描。** 第三方——Sentry 创始工程师 Ben Vinegar——专门构建了一个名为 slop-scan 的工具来衡量 AI 代码模式。确定性规则,经过成熟开源基准校准。分数越高 = slop 越多。他在 gstack 上运行了该工具,我们得了 5.24 分,是他当时测量过的最差成绩。我认真对待了这些发现,进行了重构,并在一次 session 中将分数降低了 62%。运行 bun test,看着 2,000 多个测试通过。 **评审严格性。** 每个 gstack 分支都要经过 CEO 评审、Codex 外部视角评审、DX 评审和工程评审。通常每种各进行 2-3 轮。我刚发布的 /plan-tune 技能经历了 CEO 扩展计划的范围回滚,因为 Codex 的外部视角评审发现了 15 个以上我的四次 Claude 评审遗漏的问题。评审基础设施能捕获 slop,这在代码库中是可见的,任何人都可以阅读。 ## **我将承认的内容** 我要比批评者更有力地为对方立场辩护: **全新项目 vs 维护。** 2026 年的数字以新项目代码为主。成熟代码库的维护每天产出的代码行数更少。如果你问的是"Garry 能否让团队在维护银行里 1000 万行遗留 Java 代码时提升 100 倍效率",我的数字无法证明这一点。需要其他人在不同的场景下运行自己的脚本。 **2013 年基准存在幸存者偏差。** 我 2013 年的公开活动很少。这次分析包含了 Bookface(私有,22 个活跃周),那是我那年最大的项目,所以偏差比看起来要小。但也不是零。如果 2013 年的真实速率是每天 50 行而不是 14 行,那么以当前速度计算的倍数是 228x 而不是 810x,仍然很高。 **质量调整后的生产力尚未完全得到证明。** 我没有 2013 年的我和 2026 年的我之间干净的 bug 密度对比。我能说的是:回滚率在正常范围内,修复率健康,测试覆盖率是真实的,而对抗性评审流程在最近的计划中发现了 15 个以上的问题。这是证据,不是证明。怀疑者可以打折扣。 **不同时代"已发布"的含义不同。** 2013 年的一些产品发布后死掉了。2026 年的一些产品也可能如此。如果两年后我今年发布的东西有 80% 已经死亡,那么"你建了一堆没人用的东西"这个批评就会有其道理。我接受这个现实核验。 **首次触达用户的时间才是重要的指标,而不是代码行数。** 从"我希望这东西存在"到"它存在了,并且有人在用它"的 60 天周期,才是真正的转变。代码行数是下游证据。正确的指标是"每季度发布的产品数量"或"每周可用功能数量",这些数字上涨了类似的倍数。 ## **这些代码行变成了什么** gstack 不是一个假设。它是一个拥有真实用户的产品: - 5 周内获得 75,000 多个 GitHub star - 14,965 个独立安装量(基于选择性加入的遥测数据,实际数量至少是这个数字的 2 倍) - 自 2026 年 1 月起记录了 305,309 次技能调用 - 峰值周活跃用户约 7,000 人 - 所有技能运行的成功率为 95.2%(305,309 次总运行中有 290,624 次成功) - 57,650 次 /qa 运行、28,014 次 /plan-eng-review 运行、24,817 次 /office-hours 会话、18,899 次 /ship 工作流 - 27,157 个会话使用了浏览器(真正的 Playwright,而非玩具级工具) - 会话时长中位数:2 分钟。平均值:6.4 分钟。 按使用量排名的热门技能: 这些不是躺在抽屉里吃灰的脚手架,而是成千上万的开发者每天都在使用的工具。 ## What this means 我并不是说工程师要消失了。没有哪个理智的人会这么认为。 我是说,工程师现在可以飞翔了。2026 年的一名工程师,用同样的工作时长、同样的日常工作、同样的大脑,能够产出 2013 年一个 100 人团队的成果。代码生成的成本曲线下降了两个数量级。 这个数字中有趣的部分不是体量,而是速率。而这个速率所揭示的,不是关于我个人的陈述,而是关于整个软件工程所站立的地基正在发生的变化。 2013 年的我,每天大约提交 14 行逻辑代码。对于一个有正式工作、只能利用业余时间编程的人来说,这很正常。 2026 年的我,每天提交 11,417 行逻辑代码。同时还在全职运营 YC。同样的日常工作,同样的闲暇时间,同一个人。 这种差距,并不是因为我变成了一个更好的程序员。如果说有什么变化的话,我对编程的直觉认知反而退化了。差距在于,AI 让我真正得以实现那些我一直想构建的东西——小工具、个人产品、那些曾经因构建成本太高而死在笔记本里的实验。"我想要这个工具"和"这个工具已经存在并正在被我使用"之间的鸿沟,从 3 周缩短到了 3 小时。 这里是脚本:scripts/garry-output-comparison.ts。在你自己的代码仓库上运行它,把你的数据告诉我。这个论点并不关乎我个人——它关乎的是,这片地基是否已经移动。(https://github.com/garrytan/gstack/blob/main/scripts/garry-output-comparison.ts) 它确实移动了。而最棒的是,不管你怎么看我、怎么看 GStack、怎么看逻辑 SLOC,或者其他任何事情——有一个事实是确定的:你也可以飞翔。 -- GStack 刚刚发布了 v1 版本。这是我使用 Claude Code 的方式。它是 MIT 开源协议,完全免费。点击这里试用。(https://github.com/garrytan/gstack)