当 LLM 几分钟就能写出实现时,开发者难免会问:自己是不是正在逐渐失去编程能力?Joe Woods 的回答是:使用 LLM 不一定会让人变懒,前提是你仍在决定代码该是什么样,并在结果不适合项目时及时介入。

关键区别在于:委派实现,不等于委派判断。前者仍由人定义问题、约束、设计和验收标准;后者则是不挑战模型假设,也不检查结果是否符合团队长期目标,直接接受它生成的内容。

原文来源:Joe Woods,《I Don’t Think LLMs Are Making You Lazy》:https://blog.joewoods.dev/programming/i-dont-think-llms-are-making-you-lazy/,2026 年 10 月 10 日。本文依据用户提供的完整原文整理;QA 工程实践为本文延伸,不代表 Woods 的原文建议。原网页在本次复核时无法独立打开。

工程主导权体现在围绕代码作出的决定里

代码能运行,不代表设计合理。命名、抽象、模块边界、依赖关系、错误处理、可读性和可维护性,都需要结合具体情境判断。模型可以模仿仓库现有惯例,却未必知道这些惯例背后的事故历史、组织需求和产品限制。

生成结果可能引入多余抽象、绕过既有服务边界、把断言塞进页面对象,或为了让构建通过而削弱测试。这些问题未必是语法错误,而是意图、设计和工程判断出了偏差。

与其每次聊天都重复相同要求,不如维护工程文档、审查标准、约束说明和经过认可的黄金样例。样例不只展示能编译的代码,也应体现团队希望如何组织、测试、命名和维护代码。它们也需要定期复核,不能让昨天认可的架构变成明天不可质疑的规矩。

给模型明确目标,再把实现修到合适。

Woods 把工程品味比作骑自行车:即使五年不写代码,也不一定会失去判断代码写得好不好的能力。有经验的工程师也许忘了某个 API 的具体语法,却仍能发现耦合过重、抽象不合适或缺少失败处理。

不过,品味并不会永远自动保持。读真实代码、讨论设计、调查事故,以及让同事挑战自己的假设,都有助于持续磨练判断力。

代码品味、算法记忆和工具熟练度并非一回事

Woods 坦言,他不一定能马上想起如何翻转二叉树。他说自己大约只背过两次,每次都是为了准备 LeetCode 面试题而短暂复习——那场招聘仪式,是为了让别人愿意付钱请他去写另一种代码。他认为,这不是 LLM 把知识“抹掉”了,而是这项技巧在面试之外很少用到。

他也特意补充,自己的工作确实需要掌握数据结构与算法。许多日常编程其实是在连接系统、承载业务流程、解决用户遇到的问题。难点往往是判断软件应该如何表现,以及如何用代码体现流程与良好体验,而不是回忆一道面试题。这并不意味着算法和计算机基础不重要;性能敏感、安全关键或系统底层工作可能高度依赖这些能力。更合理的做法,是按真实职责评估能力,而不是只用孤立的记忆题判断一个人是否胜任。

Woods 仍会参加 Advent of Code 编程挑战,但他也明确区分这类练习与自己现在每天面对的工程工作。

工具熟练度依然有用。

Woods 说,如今通常只有遇到问题时才会打开自己熟悉的代码编辑器——而他认为,最好避免让事情发展到出了问题才介入。编辑器快捷键已经熟到像开车时的下意识动作。他理解有人会觉得,过去投入在工具上的时间如今已经过时;但这些练习并没有白费,熟悉编辑器、调试和读代码仍帮助他指导初级工程师、建立护栏,并识别模型生成的不良代码。

这只是作者个人的工作方式,不是人人都该照做。对正在学习的人、测试自动化工程师和维护复杂系统的团队来说,亲自检查代码和调试仍然重要。

觉得自己生疏时,可以先问三个问题

自我检查问题可能的警讯可以尝试的做法
我有没有充分引导 LLM?代码能运行,却违反关键设计约束说明验收标准、禁止事项和审查要求
我是不是不再和别人讨论好代码?与模型的对话取代了同伴挑战恢复设计评审、结对和代码阅读
我是不是不再投入时间学习?会调用工具,却讲不清结果调试真实故障、学习新概念,偶尔独立解决问题

Woods 并没有要求所有人回到过去的编码习惯,而是鼓励我们认真判断:哪些变化值得接受,哪些问题需要主动解决。对他自己而言,这三方面的问题都会尽量处理。

QA 应继续掌握质量判断权

以下内容是把原文观点延伸到 QA 工程,不是 Woods 的直接建议。

关键风险不是 AI 生成了自动化测试,而是团队不再判断这些测试是否真的提供了有价值的证据。下面这段 Playwright 测试可以运行,却留下不少问题:它是否创建了真实订单?支付是否与生产环境隔离?“Success”文字是否足以证明业务结果正确?测试数据如何清理?

await page.goto('/checkout');
await page.getByRole('button', { name: 'Pay' }).click();
await expect(page.getByText('Success')).toBeVisible();

可以通过四层做法保留质量责任:由人定义需求、风险、业务不变量和预期结果;明确语义化定位方式、页面对象边界、测试夹具、断言与清理要求;实际运行测试并分析失败,适当时用变异测试或预置缺陷确认测试确实能发现问题;再通过拉取请求审查、黄金样例、技能评估和回归数据集持续改进。

下面是说明思路的策略示例,并非某个工具的配置格式:

ai_coding_policy:
  human_owns:
    - acceptance_criteria
    - risk_assessment
    - architectural_decisions
    - final_review_and_merge
  generated_tests_must:
    - assert_business_outcomes
    - avoid_invented_locators
    - isolate_test_data
    - provide_execution_evidence
  reject_when:
    - tests_only_assert_element_visibility
    - production_side_effects_are_uncontrolled
    - generated_code_cannot_be_explained

衡量完整交付成本

生成代码行数不是理想的成功指标。更值得关注的是,从需求到可合并变更花了多久、返工量、审查发现的结构问题、测试有效性、后续维护成本,以及团队成员能否解释关键决策。

生成步骤变快,可能只是把工作转移到审查、调试或事故处理中。应该从整个交付过程评估生产力,而不只看模型生成有多快。

把敲代码交出去,判断仍要自己做。

Woods 提醒我们,工程价值不只来自亲手输入代码,也来自确定方向、权衡方案、识别缺陷和帮助他人学习。

但需要保留一个边界:**“LLM 不一定让人变懒”不等于“依赖 LLM 永远不会削弱技能”。**如果人们不再理解、质疑和学习代码,能力退化的风险仍然存在。

对 AI 原生质量工程来说,目标不是让 AI 写下每条测试,而是由人掌握质量标准、风险决策和最终批准权,再把合适的重复实现工作交给 AI。

参考资料

分享