City Background
Article cover

当患有 ADHD 的工程师坐上了名为人工智能的四驱赛博轮椅

这些日子我构思了很多科普文章,但因内容琐碎,都没有办法成稿。但想法若是不能落在键盘上,很快便会化作泡影。想着不如把所有东西搅一搅,写篇「沙拉」式的文章,兴许这稀里糊涂的写作方法也能搞出一片文风独特的作品。

在这篇短文中,我想从一些基本概念开始,一步一步地介绍它们是什么。接着再跟你分享,「大语言模型」(AKA 人工智能)如何帮助我这位已经确诊的 ADHD 患者,将脑袋里那些飘荡的想法固定下来,变成可触及的作品。兴许同样受此所苦的朋友们,能够从中找到一些解决问题的灵感。

一些基本概念

ADHD

让我们先来重新审视一下 ADHD 这个概念。尽管之前我已经通过很多作品对其进行了一些介绍,但就成稿而言,依然不够直观、有力。因此开篇请允许我用另外一种浅显的方式向你介绍 ADHD 这个概念。

ADHD,又称注意缺陷多动障碍,是一种因为大脑工作模式异常导致的执行功能损伤,表现为对注意的控制能力有所缺失。

注意是什么?这是一个每个人都懂一点,但是细究却只能「谈感觉」的词。要理解它,我们得先从自身感知世界的方式说起。

我们每个人都浸泡在一个充满「信息」的海洋中。你的眼睛在不停地收集视觉信息、耳朵在收集听觉信息。不光这两个器官,我们的鼻子、全身的皮肤,都在不停地收集它们感受到的信息,并且将这些信息传递到大脑。哪怕你闭上眼睛,堵住耳朵,它们也不会真正地停止工作。

这些信息构成了一片幽暗的汪洋大海,它们无时无刻不在流动。而我们的大脑,就像是行驶在这片波涛中的一艘渔船。

渔船想要在黑暗中航行,得有一盏探照灯,点亮周遭的环境。若是风平浪静,我们可以关上这盏灯,缓缓前行。但海中若出现了鱼群,我们就得把灯点亮,照亮海面,渔夫们才能正常工作。

但如果这盏灯坏了会发生什么?

我想你脑中会冒出的第一个想法就是:灯会打不开,不能照亮海面,渔夫就只能瞎摸,丰收必然是不可能的事。

但也有可能会出现其他的情况,比如:这盏灯打开之后就关不上了,哪怕大家都应休息了,四周依然通明。不仅渔夫们不得休息,船上的电池也被快速耗光。

再比如,这盏探照灯生锈了,无论渔夫们怎么用力,都没办法改变它照亮的方向。可海里的怪物正在一步一步逼近。若是不能借着灯光找到那怪物,恐怕全船的人都会遭殃。

亦或者,这盏探照灯的螺丝松了,只要一个浪冲过来,这探照灯就会开始摇头晃脑。无聊的海面瞬间变成「迪厅」,旋转、跳跃,好不快活。

这盏探照灯就是注意力,它能照亮信息汪洋中重要的那一部分,帮助我们过滤掉不重要的信息。

而「注意力」失灵了,也不仅仅意味着「没有办法注意」(也就是探照灯打不开了)。不同患者出现的情况可能并不一致,临床上也会有不同的分类。

在我们的大脑中,负责「探照工作」的区域是前额叶(也就是额头部分对应的脑区),ADHD 患者这部分脑区的工作方式异于常人,致使他们没有办法专注地完成工作,或者没有办法适时地停止自己手边的工作。

而对于我个人来讲,ADHD 造成的最大影响便是,我没有办法完成复杂的推理工作。所有的逻辑链条都会以支离破碎的方式「漂浮在半空中」。哪怕很努力地「用双手」把寥寥几条信息拼接在一起,只要尝试伸手再抓进来一条信息,刚才手里已经拼好的东西就会重新四散开来。

这也是为什么,我上学时,在数学、物理等科目表现不佳,做开发时,也完全应付不来复杂的算法题目。

大语言模型

大语言模型,呃……是一种,比较复杂的数学模型。

That’s it!

我发现身边的人常对它抱有不切实际的期待,但实际上它并不是某种水晶球或者魔法小盒。如果非要找一种粗暴的理解方式,你可以把它看成一个参数超级多的线性回归模型(但事实上它既不线性,也不回归)。

在面对一个线性回归模型时,投入几个数字,模型就会吐出一个数字。比如,如果你希望根据婴儿的年龄预测它们的身高,那你可以构建一个简单的回归模型,把年龄当成因变量,把身高当成自变量。

准备一些数据,过一遍最小二乘法,得出来了一个漂亮的公式,我们就能用这个模型来做预测啦!

但是在开始预测之前,让我们一起来思考这样三个问题:

  • 假设这个模型告诉我们,新生儿每个月身高增长 2 厘米;如果我们向模型提问:一个人的年龄是 90 岁,他的身高是多少,我们会得到什么样的结果?
  • 假设我们并不知道新生儿的年龄有多大,只是照着样子随便向模型输入了一个数字,我们是否能得到准确的结果?
  • 我已经得到了一个相当精简的模型,我是否还能根据这个模型取回当时录入的原始数据?

相信具备基本统计素养的你,一定已经知道问题的答案了。

如果我们「简单地」调整一下模型的结构,把输入的数据换成文本,吐出来的就是文本啦。让我们用同样的视角来重新审视「魔法般的大语言模型」:

  • 如果我提的问题非常稀有,大模型会给出什么样的答案?
  • 如果我提出的问题非常模糊,大模型会给出什么样的答案?
  • 大语言模型真的会给出百分之百准确的答案吗?

如果你试过用很古老的大语言模型询问「如何烹饪意大利面拌四十二号混凝土」,一定会对那些一本正经的淦话印象深刻。直至后来,类似的淦话问题变多,被纳入训练集,模型才学会了应付这些「幽默感」。但谁又能保准会不会蹦出全新款式的混凝土呢?

相信你一定听说过完全用 GPT 写诉状的律师用 GPT 写论文的研究者。这些都是非常典型的,把大语言模型当成神奇海螺来用,最后搞砸一切的例子。

如果你还没听说过这两件事,请一定点一下超链接进去看看。特别是后面那片论文,配图真的是非常精彩且充满「阳刚之气」。

做过统计的朋友一定听说过「Garbage in garbage out」这句话。哪怕是面对一个专家,给一个莫名其妙的模糊问题,我们也不会得到什么好的答案,更遑论一个数学模型。

那么,大语言模型能拿来做什么?我觉得这可以被总结成两个词:整理、转化。

一个很好的整理场景是:你拿出了几篇论文,请模型分别整理这几篇论文的核心论点,再撰写一篇简短的综述,阐释几篇论文之间的关系。

事实上我曾给本科生整理过一个心理学论文阅读的反思卡片,每次读完论文之后,都回忆一下这几个问题:

  • 这篇论文回答了什么科学问题?
  • 引言部分的叙述逻辑是什么样的?
  • 实验设计的基本方法有哪些?
  • 数据分析的方法有哪些?
  • 实验结果如何回答研究者关心的问题?

将这部分整理的工作交给大语言模型实际上就是一个很好的用例。

但重点论文还是要通篇读的,这种粗枝大叶的总结只是方便事后检索,文章逻辑链条的构建和观点的发展的过程都很重要,这些信息是没办法用一句两句总结出来的。

而一个很好的转化场景是:把你要撰写的函数用三句话描述清楚,并附带对应的 API 文档,交给大语言模型,让它拟好一份草稿版本的代码,再以此为基础进行 debug。

关于这点,后面我们会再展开聊。

开发能力

接下来,让我们一起来构建整个讨论的最后一块拼图:对于一名称职的开发人员来讲,必要的认知能力有哪些?

有的人可能觉得是英语,有的人会说是数学。但今天你都读了我写的文章,那我自然是得给你一些认知科学的视角。

在我看来,对于工程师来讲,最重要的三项能力是:数论、逻辑、语言。这三者共同构成了工程领域下问题解决的通盘能力。

我们先从比较直觉的数论来聊。数论是我们理解、加工数字信息的能力。像是打纸牌、购物算价格、解数学题的时候,我们都大量的使用到了数论的能力。对于工程师而言,在图形学领域、一般算法优化领域,以及密码学领域,对数论能力的要求都很高。

接下来是逻辑能力。编写代码的过程,在本质上是将逻辑以文本的形式描绘出来的过程。我们需要大量的构建不同概念之间的逻辑关系。从微观层面的流程控制,到宏观层面的架构设计,这些每天要做的基本任务,都和逻辑能力有很强的联系。

最后是语言能力。你可能会觉得「代码都是英文,文档也都是英文,所以工程师的英文能力一定很强。」但其实不然,每天把写代码看文档当吃饭喝水一样自然的我,雅思也不过才考了 7 分而已。事实上,日常用的英语和写代码用的英语是截然不同的两种「英语」,而我们在这里所讲的语言能力也不局限在「读文档」这一件事上。实际上,写代码本身也是一种「表达」,在表达开发者究竟想要做的事情是什么。如果你读过那种烂到透顶的代码(我希望你没有),会发现它散发这一种「讲话颠三倒四自己都不知道自己在搞什么」的味道。这在某种程度上也是一种「语言能力不足」的表现。

上述的应用场景主要表现在表层的日常行为之上。而在这些具体的行为之下,这三种能力所共同构成了更加重要的问题解决能力。

数论能力的强弱决定了开发者的精力、时程安排能力。这在项目估期、排期、成本估算等管理任务上有非常重要的作用。毕竟这些因素直接决定了产品研发的成本和风险,这二者是决定业务稳定与否的基石。

逻辑能力决定了你是否能够从不同的维度思考一个问题。在严肃的商业开发场景上,从具体的业务逻辑编写,到架构、产品、团队协作等问题,均需要不同层次的思考。很明显一个项目究竟是否成功,技术水平的高低并不是唯一因素。而能逻辑能力的强与弱,直接决定了能否将其他因素一并纳入思考的脉络。

而语言能力,则扮演着最为重要的作用:开发者究竟是否知道自己在做什么:能否能清楚地论述自己在做的功能是什么,在处理的问题是什么。这不仅对于任务汇报、同事沟通很重要。对于开发者自己来讲,如果不能用三句话讲清楚自己现在正在做的事情,那整件事情大概率就是糊的。

这也是为什么小黄鸭重要:如果你不能自动化地勾勒任务的轮廓,那么至少需要有一个「脚手架」帮助开发者把所有事情都清晰地罗列出来。只有这一点清晰了,对架构的设计、对未来的思考才是可能的,在优化算法的时候,才知道具体要优化哪些指标。

相信我,你的人生中一定会遇到小黄鸭也救不了的同事。That’s exactly how things fucked.

整体而言,对于不同领域的开发工作者、以及在不同职级的工作者,对于这些能力的要求并不一样。

比如对于偏业务的开发者,像是 Web 前端工程师,更需要良好的语言能力和逻辑能力,数论则并不那么重要。特别是着重绘制界面的岗位,能够充分理解产品策划、设计师的意图,表达清楚自己要做什么以及怎么做至关重要,而考察算法能力是完全是无效的筛选策略。

对于比较偏架构的开发工作,比如基建团队,逻辑能力是更加核心的认知能力。因为这类工程师需要大量思考不同的使用场景,对通用业务进行组织、抽象,反复的在不同抽象层级跳跃、对各种指标需要有明确的量化思考、对业务不同阶段的发展逻辑也许要有清晰的认知。我们很难想象一个艺术家性格的开发者被安排在这个岗位上,会产生多么奇幻的场景。

而计算机图形学、密码学、算法优化这类工作要求开发者频繁接触大量的计算过程和数学概念,这可并不是「数学白痴」(比如像我)能驾驭的领域。

此外,职级越高,对三者的综合要求越高。这也是为什么开发这条路不一定能走得长远,因为筛选机制就摆在那里,时间到了才发现技能点没点满就太晚了。

蟹化

蟹化(Carcinization)是指不同的甲壳动物在进化过程中独立地演化出类似蟹的形态的现象。尽管这些动物的祖先可能并不是螃蟹,但经过多次独立的进化,它们逐渐发展出扁平的身体、短小的尾巴和类似螃蟹的步足结构。

这种现象被认为是一种趋同进化的例子,说明了蟹形态在某些环境中具有适应优势,比如更好的移动能力和防御能力。蟹化的例子可以在不同的甲壳动物类群中观察到,包括一些寄居蟹和其他非蟹类的十足目甲壳动物。

ADHD 患者最大的问题是难以将注意力持续维持在一件工作上。

我所遇到的问题是没办法专注在推理的过程上,而不是推理能力本身有什么问题。抛开因为 ADHD 导致的「发言支离破碎」「逻辑一塌糊涂」,单就纯粹的推理过程本身来看,只要任务自动化到「不需高度注意力维持」,我所产出的结果并不比一般人差。相信很多 ADHD 患者都会有同样的感觉。

你当然可以拼命地勉强自己,但这并不是一个可持续的路子,因为这种勉强没办法坚持太久,而且事后会让你觉得非常疲劳。

事情一定要做完,不能一直拖着。所以被医生认证的 ADHD 患者,我本人「蟹化」出了一套不同的认知策略来解决这个问题:把任务放进「默认网络」里来做。

默认网络(Default Mode Network, DMN)是大脑中的一个网络系统,主要在我们不专注于外部任务时活跃,比如在休息、做白日梦或自我反思的时候。可以把它想象成大脑的「待机模式」。

当我们在思考过去的事情、计划未来或者进行自我反省时,默认网络会变得活跃。它涉及到几个大脑区域的协作,比如前额叶皮层和后扣带回皮层。

这个网络帮助我们处理内心的想法和情绪,是我们进行自我意识和社会认知的基础。简单来说,默认网络就是大脑在“闲暇时”的活跃状态,帮助我们进行内在思考和情感处理。

我的大学老师曾经这么描述我:「在学校里面高速穿梭,带着耳机一言不发,打招呼也不一定回」。

这基本上就是我日常的行为状态,平时「白日梦」的时候基本都是在一遍一遍一遍一遍地重复自己要做的事情。比如如果要做一个报告,可能就是在一次一次地在心里过要讲的东西,写书的那段时间,就是在重复地在大脑里面进行「试错」。

总而言之就是「把脑子放在那边让它自己运转,并不尝试主动去给它施加外力,想到哪里算哪里,一直等到事情想清楚为止就好」。看起来挺佛系,但实际上还挺好用的。

接下来就是把想清楚要做的事情一条一条列出来,按部就班地做。当然因为在具体执行的时候还是会遇到没有办法专注的问题,所以我之前的作品都是「短小」的内容,像是短篇文章,或者很小的软件库。

如果要做大东西,就只能靠「意志力」硬肝了。啊,对,你一定能想象那种典型 ADHD 患者的工作状态,「非常努力地摸鱼」、「熬夜摸鱼」。

年轻的时候这么搞是没什么大问题的,但是随着体力不断下降,事情就开始变得麻烦起来了。毕竟熬一个晚上可能就意味着接下来要难受三天,这笔帐怎么算都很不划算。

作为赛博轮椅的 AI

但好在我们都生在这个人大语言模型鼎盛的时代,事情变得相对简单了一些。大多数在线 AI 聊天服务都有免费配额,掌握好每个模型的脾气秉性后,把所有服务拉开一排,一个个对着配额按日用爆,最终就可以产生非常不错的结果。

以我最近正在做的 Rune 为例,这个项目里超过 70% 的代码全是由大语言模型撰写的。我只负责把大语言模型输出有 bug 的代码修好,写 commit message 记录修改,再提交。

这是一个不断制造拼图、并把拼图拼成作品的过程。开发的过程和前面的「蟹化后的思考模式」完全一致。在闲暇时,我的大脑几乎被思考工程设计填满,在排好重要性列表后,就开始从最重要的事情做起,把每个大任务都切成「能用三句话描述清楚的小任务」,喂给大语言模型,让它吐出可用的代码。

Rune 最一开始完成的任务是重新实现索尼的 12 Tone Analysis 算法,并且制作一个推荐系统。我过去是做脑科学的,必然对音频分析没有任何经验,于是先操起了 Perplexity 列出了主流的解决方案,然后一个一个读过去,做成笔记,敲定自己最后需要使用的方案是什么。

因为 Rune 用了 Rust 来开发,而很多软件包并不是用 Rust 写的,于是我们就把源代码喂给大语言模型,请它输出一个翻译过后的初稿(这是大语言模型非常擅长的工作,任务明确、思维链短),然后我再来修正里面写糊的部分,像是 Rust 里非常典型的借用问题。

当然有的时候修烦了也可以把报错直接贴到聊天框里,换两个模型反复折腾几次最后也都能修个七七八八。

将已经有的分析过程和音频解码库、向量数据库整合的过程也基本遵循同样的过程。我先大致阅读一遍各个库的文档,确认这些库符合我的需求,然后再把需要用到的文档片段粘到聊天框里,最后附上描述任务的「三句话」。以此流程循环往复,最一开始只有 CLI 的播放器雏形就写好了。

至此,Rune 有了最基本的播放功能、推荐功能、媒体索引管理功能。接下来要做的就是画界面了。

用大语言模型画界面几乎是不可能的事情,因为「一问一答」的形式决定了你不可能让它对着眼前的界面上上下下左左右右红橙黄绿,以及用回第一稿。特别是调整复杂动效的时候,还是得一个人蹲电脑前面跟坐牢一样「降智输出」。

此外,前后端沟通的协议设计我也没交给大语言模型做,毕竟这一步能够很好地帮助我「想清楚要做的设计究竟为何」。但 API 定义好之后,前端的数据整形和后端的增删查改,我就毫不客气的丢给模型做了,毕竟没人想写口水代码。

「能用三句话讲清楚的事情就交给模型写,三句话讲不清楚的东西就拆成好几个能用三句话讲清楚的事情,再扔给 AI 写」,这是我在开发 Rune 时使用的最基本方法论,现在你也学会了。

但请小心,这里有一些比较危险的情况。比如 Google 的模型曾经写出过会把硬盘文件覆盖的破坏性代码;再比如,大语言模型写出来的代码质量其实都在「职务代码」的基本水平线上,你不能期待它能写出什么「对仗工整」的东西,一切都维持在「勉强能用」的水平上。

关于模型的选择上,GPT 这边比较擅长做一些平铺直叙的工作,Claude 更适合需要做复杂抽象的场景,如果你需要更多的启发和建议,Gemini(Bard)则是更好的选择。

每个模型的脾气秉性都不一样,因此在「指派」任务的时候得对眼下要做的活有非常清晰的认知。

我做抽象的原则一般都是「三次定理」,一段逻辑用到第三次就丢给模型做抽象。按理说简单抽象应该交给 GPT,复杂抽象应该交给 Claude,但有的时候脑子不清楚把一些简单任务扔给 Claude 之后,输出的「宏伟奇观」不禁让人跪地不起:「大哥,这么简单的事情不至于给我搞这么复杂吧……」

科学妄想

你经常能在各种「AI 博主」的视频上看到非常严重的「魔法阵营妄想症候群」:仿佛随便讲两句话,一个软件就能平地高楼起,你只需要端着茶杯优雅地看着电脑上哗哗地输出代码。

但这并不是真的。

在开发 Rune 的过程中,我并没有因为使用大语言模型而减少自己的工作时间,甚至群友会说我每天「看起来比上班工作量都大」。

大语言模型只承载了将「定义清晰的问题转化为代码」的过程,但是它永远不能降低对开发者的能力要求。像是提出问题、解决问题的能力,最基本的架构思维,还有对于「什么是好代码」的基本判断能力。

没有这种能力,一个所谓的「开发者」最多只能写得出「导航站」、「番茄钟」、「账本」这种「白月光」项目,还是不带一丝「料」的那种。

是的,AI 不是「帮你写代码」,它做的只是「把你的描述转化成代码」。这一版本的 AI,其功能自始至终都没有脱离「组织」和「转化」。

而因为用大语言模型省下来的时间,应该被用来思考「如何把一件事情做得更好」,而不是进行某些「以 AI 为核心的诡异宗教活动」。

最典型的「宗教妄想」就是「工程师」这个行业会被彻底淘汰。随着大语言模型带来的产能提升,昂贵的人力成本的确会在某种程度上被削减,但是真正专业的软件开发工作者一定会留下:因为我们需要有人来驾驶那架高达,一家公司里也绝对不会只有区区几个驾驶高达的人。

毕竟一方面,不同的细分开发领域都有其专业性,一个庞大复杂的项目必然需要具备不同背景的「驾驶员」完成不同的任务。另外一方面,整个行业都在水涨船高,因为大语言模型而产生的生产力爆发,会带来更快的产品迭代,为了赶上更加高速的变化,必要的人力势必不会减少到危及一个行业的程度。

当然,我们也得承认,在大语言模型的加持下,暴力内卷,大量完成不具不可替代性的任务已经不再是保住工作的法宝。唯有保持思考、保持对问题的准确洞察、保持对解决途径的灵敏嗅觉,才能在这场「虚假的大灾变」当中存活下来。

我的建议

写代码依然不是一件「AI 博主」口中的「容易事」,学习写代码也不是「学习如何使用 Codeium」那么简单。你依然需要投入时间,投入大量的时间,成为一个「看起来很厉害的人」。

我在这里会向各位提供的三个建议是:

首先,学习一门强类型语言,达到 Senior 的程度。务必确保自己对于所有的基本开发范式都有所了解。这是完成「大型复杂工程」的必修课,谁都逃不掉的。在一门语言上学到的知识和经验可以非常快速地迁移到其他语言上,而学习过程中培养起来的底层能力,也能帮助你更加顺利地完成日后的开发工作。

其次,不要害怕把手弄脏。先上手写,自己写不出来就扔给 AI 写,持续不断地写下去,你手写的部分会慢慢变多,AI 写的部分会慢慢变少,写着写着就学会了。

最后则是对待错误的态度。不要害怕犯错,开发的过程本质就是探索的过程,探索一定伴随着试错,这是放之四海皆准的道理;接纳、面对错误,发现错误就及时修正它,不要想着「现在很忙,以后再修」,除非你想看见它变成巨兽回来咬你屁股的恐怖光景。

我必须坦诚地向各位讲,在开始开发 Rune 的时候,我并不懂 Rust,也不懂 Flutter,哪怕写到现在,也只是达到了刚入门的程度。软件能写得出来,全靠当年写 TypeScript 留下来的「代码直觉」。

但仅凭这些直觉,和一个个大语言模型,我这种 ADHD 患者也能坐上赛博轮椅,写出一个五万多行代码的庞大工程。

难道这不酷吗?这完全符合我对未来的想象。

以上就是今天我想向大家分享的所有内容啦,莉莉爱你 ❤~

Comments

Loading animation

Loading comments...