
大家好,我是阿辉。
最近我观察到一个让我有点凉的现象:
用 AI 重度写了三个月项目的人,代码烂得比以前快十倍。
不是个例。我手里跟踪的几个 AI 重度使用的项目,无一例外——三周内开始重复造轮子,一个月内目录失控,三个月内就到了"看一眼想离职"的程度。
但奇怪的是,开发速度确实变快了,commit 数翻倍,需求交付变快。
为什么"做得更多"反而让代码更烂?
一、代码本来就在腐化,这不是新事

软件工程有个老定律:代码的熵只会增加,除非你主动做功。
每次需求迭代、每次 bug 修复、每次“先这样上线下次再优化”,都是在给代码加熵。这是物理定律——无外力干预时,系统的混乱度只会增加。
以前没 AI 的时候,腐化速度有多快?
经验值:一个没架构的项目,18 个月走到"重写比修复便宜"的地步。
二、AI 是熵增的加速器
但 AI 来了之后,这个时间被压缩到了3 个月。
为什么?三个机制:
1. AI 只看局部,看不到全局
你让 AI"在用户列表加个筛选",它会读 UserList.tsx,照着写一个。
它不知道:
三个月前你已经写过一个通用 FilterBar隔壁 ProductList用的是另一套筛选逻辑这个项目的约定是筛选状态走 URL,不走 store
它看不到。所以它会写一个新的筛选——和现有的两套都不一样。
结果:从此你有 3 套筛选。
2. AI 默认追加,不删除
人会重构。看到三段相似代码,会抽象成一个函数,把旧的删掉。
AI 不会。它的默认动作是"加一个新的",不是"合并已有的"。因为合并需要理解两边都在干什么——这超出它的视野半径。
结果:旧代码不死,新代码不停加。
3. AI 复制 + 轻改,不抽象
人写第二个相似组件时,会停下来想:要不要抽出共性?
AI 不会停。它会照着第一个复制一遍,改几行。
第三个、第四个组件,照样复制。
结果:相似但不相同的代码到处都是,改一处要改 N 处,N 还在涨。
三、没有架构的 AI 项目,一周就开始腐烂

我看到的典型症状:
每一个症状的背后,都不是 AI 写错了代码——
是没人告诉它边界在哪、约定是什么、什么不该做。
AI 没有错。它只是按"局部最优 + 默认追加"工作。
错的是:没人给它一个全局参考系。
四、架构是给 AI 的"熵减约束"

架构的本质是什么?
以前我会说:架构是为了让人看懂代码、为了团队协作、为了可扩展。
现在我会改口:
架构是给 AI 的全局参考系。
它告诉 AI:
这个项目有几个 feature,每个 feature 边界在哪 哪些代码必须共享,哪些代码必须隔离 添加新功能应该往哪个目录放 哪些约定是不可破的(命名、状态管理、API 调用方式)
这些信息以前在工程师脑子里。现在不写下来,AI 就当它不存在。
没有架构的项目,AI 每次写代码都是从零开始。三个月后你的项目,就是 AI 的 100 个"第一次"拼起来的。
顺便澄清一下:架构 ≠ Harness ≠ Loop Engineering
最近大家把“给 AI 加约束”这件事至少切成了三个名词,经常被混着用。我做个区分。
Harness Engineering(Agent 脚手架工程)——给 AI 配的运行时环境:
能用哪些工具(tool use) 怎么管理上下文(context window) 怎么记忆和检索(memory / RAG) 怎么拦截危险操作(guardrail)
主要是 Cursor、Claude Code、Qoder 这些 IDE 厂商在做。解决的是“AI 干活的环境长什么样”。
Loop Engineering(循环工程)——更新一点的说法,专门聚焦“AI 怎么在闭环里收敛”:
怎么循环(run → check → fix → run) 用什么信号判断“够了”(编译过?测试过?lint 过?) 怎么防止跑偏(迭代上限、回滚条件) 怎么把上一步的反馈喂回下一轮
代表实践有 Ralph Wiggum loop、verifier loop、self-correcting agent。解决的是“AI 干活的过程怎么自我纠错”。
架构——你项目里代码长什么样:
目录怎么分、模块边界在哪 哪些约定不可破 一个功能的代码该放在哪
项目方自己定的。解决的是“AI 干完之后,留下的代码长什么样”。
一句话三连:
Harness 管 AI 的环境,Loop 管 AI 的过程,架构管 AI 留下的痕迹。
更要命的依赖关系是:没有架构,前两个再强都白搭。
Loop Engineering 让 AI 能反复迭代,但“什么算对”的标准是谁定的?是测试、是 lint、是类型契约——这些都是架构的产出。架构错了,Loop 只是在错的方向上更快地收敛。Cursor 的 agent loop 也不会替你决定 useUsers 该放在 hooks/ 还是 features/users/——那是架构的事。
这也是为什么这篇文章谈的是“架构”,不是 Harness 也不是 Loop。前两者是工具厂商和 agent 框架的活儿,后者是项目方逃不掉的责任。
五、先打个底:Feature First vs File Type First

可能有读者还没接触过这两个名词,快速过一下。
前端项目的目录组织有两种主流流派。
File Type First(按文件类型划分)
这是大多数脚手架(create-react-app 等)的默认结构:
src/├── components/ # 所有组件├── hooks/ # 所有 hook├── services/ # 所有 API├── store/ # 所有状态└── types/ # 所有类型要修“用户列表加载慢”这个问题,你得在 5 个目录之间跳来跳去:components/UserList.tsx 看组件、hooks/useUsers.ts 看数据获取、services/userApi.ts 看接口、store/userSlice.ts 看状态。
一个功能散落在 5 个目录。
Feature First(按业务功能划分)
把同一个业务功能的所有文件放在一起:
src/├── features/│ ├── users/ # 这个目录里什么都有│ ├── products/│ └── orders/└── shared/ # 真正共享的基础设施修同一个问题,打开 features/users/ 一个目录就够了。组件、hook、API、状态、类型全在这。
一句话差别
File Type First:按文件类型分目录 Feature First:按业务功能分目录
前者适合小项目(官网、落地页);后者适合中大型项目,尤其是 AI 重度使用的项目。
为什么 AI 项目特别需要 Feature First?接着看下一节。
六、AI 时代,架构有了三个新职能

职能一:给 AI 圈定改动半径
Feature First(按功能划分目录)不是"程序员喜欢的目录结构",是让 AI 知道改一个功能只能改这一个目录。
AI 修改时不会越界——因为 import 边界、模块导出、目录隔离已经给了它信号。
features/users/ 改了,features/orders/ 不会被波及。
职能二:把"约定"从口口相传变成文件
团队的约定以前靠 onboarding、code review、wiki 传递。
但 AI 不参加 onboarding,也不会主动去读 wiki。
约定必须以文件形式存在——AGENTS.md / .cursorrules / CLAUDE.md。写在 AI 每次都能读到的地方。
写在脑子里的约定,对 AI 等于不存在;写在 wiki 里的,AI 也读不到。只有写在 AGENTS.md 这种标准位置,才算数。
职能三:让"什么不能做"变得 enforceable
人靠默契。AI 靠规则。
ESLint 阻断深层相对路径 TypeScript 阻断弱类型 dependency-cruiser 阻断跨 feature 引用 pre-commit hook 阻断未走 contract 的 API 调用
这些不是"提醒",是护栏——让 AI 想坏也坏不了。
七、所以怎么做

我的做法是三件事:
1. 上来就把骨架立住
第一周不写功能,先定 feature 划分、目录约定、状态管理选型。
骨架立住,AI 才有"参考系"。后面 AI 写得越快,越受益于这个骨架。
2. 把约定写进 AGENTS.md
每条约定一行,声明式:"禁止 X""必须 Y"。
不要写成长篇大论的 wiki。AI 读规则,不读散文。
3. 用工具固化护栏
ESLint、TypeScript、dependency-cruiser、commitlint——以前是为团队的,现在主要是为 AI 的。
让"违反架构"在 commit 之前就被卡住——比 review 时再喊"你这写得不对"有用 100 倍。
回到开头

代码的熵只会增加,这是物理定律。
AI 没有改变这个定律——它只是改变了系数。
以前一个没架构的项目,18 个月烂完。 现在用 AI,3 个月就到。
但反过来——
如果你有架构、有 AGENTS.md、有工具兜底,AI 反而是熵减的加速器。
它能在你设定的轨道里飞奔,每天产出大量正确、一致、合格的代码。
差别不在 AI 强不强,差别在你有没有给它轨道。
AI 越能写代码,架构越值钱。
如果你的项目还没架构,从今天开始花一周补上。
不然三个月后你回头看,会发现自己用最贵的工具,造了最快的烂代码。
你的项目用 AI 写代码后,腐化速度变快了吗?评论区聊聊。
下周二见。
夜雨聆风