灵魂不能外包
本文批判了当前AI编程工具的过度自动化趋势,主张编程的核心应保留人类的思考与设计意图。作者认为理想的工具应像‘递砖的助手’而非‘盖房的机器人’,通过函数级生成、注释驱动、主动触发等方式增强开发者对代码的掌控感,避免心智负担爆炸和代码质量下降。文章强调‘Human in the Loop’的重要性,并指出业界盲目追求全自动生成的风险。
灵魂不能外包
我越来越不喜欢现在这些AI写代码的工具了。
不是说它们完全没用。我承认,对于那些千篇一律的CRUD,对于市面上已有的套路组件,它们确实可以做到你一句话下去就生成一大堆代码。但问题就恰恰出在这里——它生成了一大堆。一旦我做的是一些真正前沿的、创新性的东西,是一些世界上从未有过的逻辑,这些工具生成出来的东西就永远不能真正理解我的意图,永远没法严格按照我的要求来。它们只是吐出一些看起来对了、但内部逻辑一团乱麻的东西。这不是在帮我,这是在给我塞过来一张我根本看不懂的草图,然后告诉我说“你就照着这个改吧”。
我想象中真正好用的工具,不应该是这样的。我不需要一个替我把整个房子都盖好的机器人,我只需要一个在我砌墙时默默递砖的人。换句话说,我要的是Human in the Loop——人始终在环内。我想在IDE里写注释,用自然语言清晰地告诉LLM我这一段要干什么,然后它读取我的注释,结合项目里已有的代码,帮我生成实现。但这生成不是一口气来一大堆,而是以函数为单位,以类为单位。一小块一小块地交付给我。这样我心智的负担是可控的,我对代码的细节会了解得更多,而不是面对一坨看起来对了、实际上自己都不敢动的庞然大物。 ![[file-20260620161943819.png]]
为什么是注释?因为注释是我和机器之间最诚实的契约。当我在注释里写清楚“这个函数接收已排序的列表,用二分查找返回目标索引,没找到就返回-1”,我其实已经把最重要的设计做完了。剩下的翻译工作,AI可以代劳。而为什么必须以函数为单位?因为人的注意力是有限的,一次性拿到两百行代码,我需要逐行审查,需要在自己的脑子里重新建一遍它的逻辑,这比我从头手写一遍还要累。但如果每次只生成一个函数,我花五秒钟审阅,接受,再写下一段注释,再生成下一个——这样代码的所有细节始终在我脑海里流淌,不会出现那种“看着好像没问题,三个星期后调试到崩溃”的灾难。
顺着这个思路往下走,你会发现另一件让我越来越不耐烦的事情:现有的工具还在强迫我用记忆来编程。以前,资深开发和初级开发一个肉眼可见的分水岭,就看谁对语言命令更熟悉,谁对常用库的函数签名记得更牢。有时候我很久不用一个库,那个函数名就在嘴边但死活想不起来,结果只能用复杂得多的方法绕一大圈,而其实那个库本身就有一个函数可以秒杀。现在有了LLM,这种“检索性知识”根本就不该再占用我的脑容量。我需要的是,我清晰地知道自己要什么输入,要什么输出,业务逻辑是清楚的,然后剩下的、那些“怎么调用那个库”、“参数按什么顺序传”的琐碎事,全部交给AI去处理。
这也就意味着,编程在我眼里正在回归它本来该有的样子:我思考“要什么”,机器负责“怎么调”。当我在Python里写下一个deduplicate_and_sort(items),我不想知道最后是sorted(set(items))还是用pandas的drop_duplicates加sort_values,我只关心“去重并排序”这件事本身。如果工具有足够智能,它甚至应该在我写完这个函数名的时候,就直接帮我把这一行替换成最简洁的实现,然后安静地退回去。我是在定义意图,不是在当人肉搜索引擎。
可你看看现在市面上的那些补全工具,它们全都在往死里磕延迟,好像谁先弹出幽灵文本谁就赢了。我实话实说,我在用的时候根本就不在意所谓的延迟。Copilot提醒得太快了,我有时候会很烦。你懂那种感觉吗?我正在流畅地敲着代码,脑子里还在酝酿下一步的走向,它突然啪一下弹出一大段建议,就像你正讲到兴头上旁边有个人不断抢你的话。这打断我的思路,让我不舒服。Copilot其实也允许你调整触发的延迟时间,但无论你怎么调,它总是不太对劲。因为你每次面对的问题不一样,思考的复杂度不一样,你需要的安静时间肯定也不一样,没有一个固定的毫秒数能适配所有场景。所以我觉得,与其让它在那里猜什么时候该出现,不如干脆换成主动触发的形式——就像一个一直站在你身边的大神,他从不好为人师,从来不会在你不需要的时候跳出来指指点点。只有当你真正卡住了,主动喊他一声,他才会开口。你按下一个快捷键,或者做一个什么手势,那一行幽灵文本才飘出来,给你一个开头,给你一点启发。它是在为你留出完整的思考空白,而不是在跟你比谁手快。工具到底尊不尊重人,从它懂不懂什么时候该闭嘴就能看出来。 ![[file-20260620162050655.png]]
这背后是我一直坚持的一个信念:人类的思考在很多时候都是宝贵的。我珍惜我的思考,虽然他可能一开始并不完备,但是他的可成长性比AI直接给我的任何东西都要强得多。你仔细想,当我亲手写下一个函数签名、定义好几个关键分支,哪怕只是几行伪代码,我就已经把我的设计意图做了第一次具象化。这时再让AI去填充细节,它的上下文就不再是“猜你想做什么”,而是“基于你已经明确的骨架去完善”。出错的空间会骤降。而反过来,如果从零直接生成,我不得不在大脑里把它的逻辑全部重跑一遍,认知成本高到离谱。而且我自己的实践经验一再告诉我:你手写出来的代码叫AI去改,反而比LLM从零开始生成要快速准确得多。因为你手写的那部分已经锁死了架构决策、接口边界、状态管理策略,AI要做的仅仅是填充方法体、优化表达式、补全参数映射,这些都是它擅长且不容易跑偏的活。 ![[file-20260620162132324.png]]
我想做的工具,或者说我理想中的那种编程环境,核心目的就是增强人类写代码时的思考,让写代码的人能专注于“怎么实现”,而不是去背那些该死的代码API。这样你对你自己的项目的掌控感才会真正变强,你才不会在一堆AI吐出来的代码海洋里随波逐流。
可是现在整个行业的风向是很危险的。我看市场上这些AI生成工具,它们默认的都是人类终将退场的大跃进叙事,说白了就是为了赚融资的噱头。对于做业务做应用的程序员,这些东西也许还凑合,但对于搞研发、搞前沿探索的人,这些工具根本就不适配。它们话里话外的预设都是代码百分之百由AI来写。而我看到的现实是,这根本不是未来才要担心的某种尽头,这就是今天已经泛滥成灾的主流用法。那些自媒体吹嘘的“一锤子买卖”——一次对话就生成一个日历应用、一个Todo清单——只是赚眼球的表演,真正在干活的程序员其实也是把需求拆成一个个小任务,一点一点慢慢磨。但问题在于,如果你依赖的是Chat式的生成,你很容易一次性拿到好几个文件,心智负担一下子炸开,看都看不过来,根本不敢乱改。不敢改怎么办?只好继续叫AI改,越改越大,越改越乱。测试也是AI写的,自己也不知道是不是真的过了,反正AI写的用例跑通了,鼠标去页面上点两下看着好像没问题就算过了。至于内部逻辑是不是真的对,没人再管了。现在很多程序员就是这么写代码的,然后跑到GitHub这种社区去拉屎,提交那些没人看得懂的PR。项目的维护者也不知道怎么看,只好也叫AI看,AI进去跑一遍测试,做几次review,看着没问题就合了。 ![[file-20260620162025875.png]]
而如果换成代码补全,情况就完全不同了。内联补全的使用方式天然就是小步快跑,天然逼迫你把问题拆成原子化的片段。你一次只面对一个函数的生成,一次只审查一小块逻辑,心智负担始终被控制在一个可以内化的范围内。它不是“一锤子买卖”,它要求你不断地定义意图、接受建议、再定义下一步。这种节奏,反而更接近我们真实思考问题的方式——先把大的拆成小的,然后一个一个小地解决,每一步都是你自己做的决定。
我觉得不应该是Chat那种。珍贵的思考全部被丢掉了。究竟谁才是AI的主人?我不接受一个默认人类会退场的编程环境,我要的是一个反异化的、人类永远拿着决策权、AI永远只是执行者的环境。我决定做什么,它负责怎么做。任何AI的变更,哪怕只是改了一行,都必须呈现为可逐行接受的Diff,不存在自动合并这种事。测试的核心断言,必须由我亲手写下,因为那是我对“什么才是正确”的唯一主权宣示。
把这些想法捏在一起,我想要的工具其实已经在脑子里很清晰了。它必须是自托管的。我说的自托管,不是说非要自己去买服务器,而是这个工具本身不能有遥测代码来偷偷监控我的使用习惯,不能把我的数据上传到什么云端去分析。背后的LLM服务,我必须能自由选择:我可以本地部署一个开源模型,也可以随时切换成任何一家提供商的API,而不是被绑死在Copilot或者某一个特定的服务上。我的代码永远不出我的机器,我的使用数据也永远留在我自己的手里。它的交互形态是纯粹的内联补全,不是Chat,不是侧边栏,就是幽灵文本。它沉默,在我快速敲击的时候彻底安静,像不存在一样。只有当我主动唤起它的时候,它才会出现,给我一小块建议。它可以让我用注释驱动,也可以让我先手写出函数签名和骨架,然后只在我需要的时候填充细节,并且严格守住边界:一次只给我一个函数或者一个类,绝不多给。至于API细节,它应该直接帮我把“去重排序”映射成项目里最合适的那行调用,把“通过消息总线通知用户”翻译成我们内部框架的具体方法,我不需要记,我只需要把意图说清楚。而测试,行为的描述由我来写,断言由我来写,AI只帮我生成辅助代码和脚手架。对“正确”的定义,必须永远攥在我自己的手里。 ![[file-20260620162106231.png]]
说到底,我不是在找一个更快更会猜的补全工具。我是在找回写代码作为一种思考活动该有的尊严。我不想让AI替我思考,我要它帮我更好地思考。而这一切的根本前提是——我是我代码的作者,AI是我的工具,而不是反过来。