ARTICLE DETAIL

建站实战干货

来自一线的建站与推广经验沉淀,每一条都经过真实交付验证。

AI生成代码可读性提升:从提示词到审查的完整实践

2026/9/30 0:46:34 拓冰建站 浏览量
AI生成代码可读性提升:从提示词到审查的完整实践 最近这大半年我明显感觉到AI编码工具已经变成了团队里的标配。每天Pull Request里都有大段大段的AI生成代码提交速度确实快了不少。但随之而来的一个很现实的问题代码是变多了能让人一眼看懂的部分却没跟着变多。AI生成代码的可读性正在成为代码审查效率的最大瓶颈也是后面维护成本里最容易爆雷的一点。怎么说呢AI写代码特别像一位工作效率极高但性格莽撞的新同事他能在两分钟内把功能写完但他不会主动考虑读代码的人怎么想。你要是不在提示词和审查环节上做约束他就能给你造出一座由魔法数字、深层嵌套和无意义变量名组成的抽象迷宫。这篇文章我想从实际踩坑的角度把“让AI生成代码更好读”这件事拆开聊透——先看问题出在哪再看怎么调教AI、怎么在审查时把关最后聊聊维护阶段怎么让可读性不滑坡。适合正在用AI编码工具的开发者也适合需要给团队定代码规范的负责人。1. AI生成代码的可读性问题出在哪1.1 典型问题模式嵌套过深、命名敷衍、逻辑绕远路先说最常见的三类问题基本每个用AI写代码超过两周的人都见过。第一类是嵌套地狱。AI特别擅长用if套if再套if每层缩进都像是在跟你玩套娃。比如让它写个数据校验逻辑它可能生成这样的代码def validate_order(order): if order is not None: if order.items: if order.items[0].price 0: if order.customer: return True return False功能上没错但读起来像在爬楼梯——你要看到最后一个return True得先在心里把四层if全部解开。这种代码在改动时特别容易出错因为你根本看不清哪一层对应哪个条件。第二类是命名敷衍。data、temp、res、list1、result2这种名字在AI代码里出现的频率高得吓人。有一次我审查一个Python脚本里面有个变量叫data2它其实是订单金额的累加结果。过了三天我自己去维护这段代码完全想不起来这个data2到底是个什么东西。AI生成代码时是按概率来选词它并不会去理解这个变量在业务里的含义所以倾向于给一个最“通用”的名字而这个“通用”在代码里基本等于“无用”。第三类是逻辑绕远路。AI在生成复杂业务逻辑时偶尔会用一个异常复杂的表达式绕一个大圈只为了实现一个本该非常直接的功能。比如它可能为了合并两个字典先生成一个列表再用dict.fromkeys转一遍。这种代码运行没问题但读代码的人会不断产生“你为什么要这么写”的困惑。1.2 为什么AI会生成这些代码概率生成的本质要理解这些问题得先想清楚AI写代码的工作方式。目前主流的代码生成模型本质是在做“下一个token最可能是什么”的预测。它见过海量的开源代码知道在某个上下文里出现什么样的代码段最“像样”——但它并不知道这段代码将来会被谁读、会在什么场景下被改。这就导致了一个核心矛盾我们人类写代码时脑子里有一张三张图——功能图实现什么、结构图代码怎么组织、读者图谁会来读。AI只有前面半张它追求的是“在这个位置生成一段合理的代码”而不是“让这段代码最大概率被同行理解”。所以AI生成的代码经常局部合理、整体松垮变量名不承载语义控制流不表达意图注释也只停留在“代码在做什么”而不是“代码为什么这么做”。明白了这一点你就会理解为什么靠“提醒AI写好一点”是没用的。你得把可读性的要求变成明确的约束塞进上下文里逼着它在生成阶段就遵循人类的阅读习惯。2. 提升AI生成代码可读性的核心原则2.1 命名规范让名字自己解释一切想让AI生成的代码可读性上去第一条要攻的就是命名。我们的目标不是“有个名字就行”而是“任何人看到这个名字不用看上下文就知道它是什么、用来干嘛”。我整理了一套给AI用的命名约束实测下来效果相当好布尔变量用is_、has_、can_开头比如is_available而不是available_flag函数名用动词开头比如fetch_invoice而不是invoice_processing集合类型用复数名词比如orders而不是order_list表示耗时或计数的变量带上单位比如timeout_seconds而不是timeout禁止出现data、temp、res、list1这类无意义名字。在提示词里我会直接把这些规则写进去并且提供一个对的例子。比如请用以下命名规范生成代码 - 布尔变量使用 is_/has_/can_ 前缀 - 函数名使用动词开头 - 集合变量使用复数名词 - 禁止使用 temp、data、res、list1 等无意义命名 示例 # 错误def process(x): data load(); y calc(data) # 正确def calculate_total_amount(invoices): return sum(invoice.amount for invoice in invoices)有读者可能觉得这样写提示词有点啰嗦但你想AI生成一段代码只要几秒钟你花几十秒把规范说清楚换来的是你后面读代码、改代码时节省的几十分钟。这笔账怎么算都划算。2.2 结构化控制流扁平化优先嵌套控制在两层以内AI生成的控制流特别容易滚成一团。要让代码好读核心原则是“扁平化”。我在团队里定了一条硬规矩嵌套深度超过两层就要想办法拆。最常见的扁平化手法是“卫语句”。把异常情况、边界条件提前返回让主流程留在后面平铺直叙地走。比如前面那个订单校验的例子优化后是这样def validate_order(order: Optional[Order]) - bool: if order is None: return False if not order.items: return False if order.items[0].price 0: return False return order.customer is not None每个条件都是一个独立的“关卡”一眼扫过去就知道每个条件拦的是什么。另一个扁平化手法是“提取函数”。当一个函数里有明显可以独立成块的逻辑就让AI把它抽成单独的函数用函数名表达意图。这里的判断标准是一个函数如果超过15到20行或者你读的时候需要停下来想两次就该拆了。我在提示词里是这样约束AI的控制流要求 - 嵌套层层级不超过2层 - 所有边界条件和异常情况使用卫语句提前返回 - 函数体超过15行时必须拆分为多个小函数 - 避免过度使用三元运算符和 lambda除非能显著提升可读性实际经验告诉我加了这些约束之后AI生成的代码虽然不会从“惊艳”变成“完美”但至少从一个“让人皱眉头的黑盒”变成了“基本能顺着读下来的普通代码”。这正是我们需要的——可读性的目标从来不追求天才般的优雅而是追求让读代码的人少死点脑细胞。2.3 注释策略告诉读者为什么而不是重复在做什么AI生成注释有两个极端要么完全忘写要么写出“废话文学”级别的注释。比如total 0 for item in items: total item.price # 累加价格这种注释就是把代码翻译了一遍一点信息量都没有。真正有效的注释是什么是解释为什么这么写、为什么不那样写、这里有什么坑。比如# 这里不能直接用 sum(items.price)因为 price 在历史数据里可能是 None # 所以手动累加并在累加时做空值跳过 total 0 for item in items: if item.price is not None: total item.price你看读完这段注释你理解了作者面对的数据约束下次修改时就知道该注意什么。我给AI的注释规范是这样写的注释规范 - 注释解释“为什么这么写”不解释“代码在做什么” - 如果代码本身已经很清晰不要写注释 - 在涉及业务规则、边界条件、历史包袱的地方必须写注释说明原因 - 禁止写“这是一个XX函数”“XX变量表示XX”这类描述性废话这个约束在多数模型上是有效果的但有时候AI还是会生成一些“代码说明书”这时候就需要人工审查环节去把关把废话注释直接删掉。3. 实操用提示词工程让AI一次生成高质量可读代码3.1 一份可以抄作业的提示词模板讲了这么多原则直接给一套我目前用得比较顺手的提示词模板你可以根据自己的场景改。请帮我写一个[功能描述]的[编程语言]函数/模块。 要求 1. 命名规范 - 函数名用动词开头布尔变量使用 is_/has_/can_ 前缀 - 集合变量用复数名词避免使用 data、temp、res 等无意义名称 2. 结构要求 - 嵌套层级不超过2层边界条件用卫语句提前返回 - 单个函数不超过15行超过就拆分成多个小函数 - 不要让函数有“隐性副作用”如果需要修改外部状态请明确说明 3. 注释要求 - 注释解释“为什么”不解释“做什么” - 涉及业务规则时必须在注释里说明背景和约束 4. 输出要求 - 先给出完整代码再附加 3 条阅读提示说明这段代码的关键设计意图你可能会好奇第4条“阅读提示”是干什么用的。这是个很妙的小技巧让AI在生成完代码后额外输出它自己对这段代码的理解。这一步有两个好处第一是逼迫AI在生成时多想一步“这段代码满足什么意图”第二是给你审查时提供了一个快速了解代码的入口。你会发现自己读代码的速度明显变快了。3.2 用代码格式化与重构手段兜底哪怕提示词写得再好AI偶尔还是会交出一些结构丑陋的代码。这时候不要手写改全部直接让格式化工具和重构手段来兜底。团队里可以统一启用类似ESLint、pylint这类带可读性检查的Lint工具。它们至少能帮你拦住一部分明显问题比如过长的行、未使用的变量、过深的嵌套。代码提交前强制跑一遍format保证风格统一这也能让AI生成的代码和人类写的代码在格式上没有割裂感。如果AI生成了一段烂代码我的做法不是让它“再写一遍”而是给它具体的修改指令。比如代码可读性需要改进请按以下要求修改 1. 把嵌套的 if 改成卫语句 2. 将变量名 data 改为 order_amount 3. 把这段逻辑拆分成两个函数parse_order 和 calculate_discount这样做的成功率远高于“请优化这段代码的可读性”。因为“可读性”这个词太抽象模型不知道该从哪下手但“改掉这个嵌套改名、拆分”是具体的操作模型执行起来非常稳定。4. 代码审查中如何给AI生成代码把关4.1 审查要点清单先看可读性再看正确性团队里引入AI编码工具之后我把Code Review的检查顺序调了个个。以前是”先看功能对不对”现在是“先看代码能不能懂”。因为一个没人能读懂的代码就算功能对了三个月后需要改的时候也一定会坏。下面是我给团队整理的一份AI生成代码审查清单直接贴出来供参考检查项关注点AI常见问题命名质量变量/函数名是否准确表达语义大量使用data、temp、x1之类无意义命名控制流结构嵌套层级是否过深是否能扁平化if套if套if把简单逻辑写成多重嵌套注释质量是否解释了“为什么”而非“是什么”要么没注释要么注释是代码的逐行翻译函数粒度单个函数是否过长是否职责单一一个函数干三件事参数列表长得吓人业务规则实现是否符合领域逻辑生成通用逻辑但遗漏了重要业务约束冗余代码是否存在未被调用的分支或重复逻辑生成时多写了一些防御代码导致逻辑混乱每次审查我要求至少把“命名质量”和“控制流结构”这两项过一遍再合并。其他几项如果时间紧可以拖后但命名和控制流是“一眼就知道bad”的项目过了这关才算有资格进主干。4.2 自动化审查与人工审查怎么各司其职自动化审查能解决“风格统一”和“明显缺陷”这个层面的问题但它替代不了人类判断。Lint工具可以告诉你“这行超过了100个字符”“这个函数有10个分支”但它无法告诉你“这个merge_data到底是在合并什么数据这么命名会不会误导维护者”。后者的判断需要领域知识需要理解业务上下文需要知道这个模块将来会怎么演化。这是人该干的部分。不过有一个AI辅助审查的小技巧可以分享让AI自己审一遍自己生成的代码。你可以在代码生成之后让模型站在“一个陌生工程师的视角”评价一下这段代码的可读性并给出修改建议。比如请把下面的代码当作一个首次接触这个项目的人来阅读指出你最困惑的三处地方并解释为什么困惑 [粘贴代码]这个做法经常能揪出我一开始没注意到的命名或结构问题。因为模型不用考虑维护者的面子它的“困惑”其实就等于普通读者读代码时的真实体验。人工审查时我还有一个习惯凡是AI生成的代码我会多问一句“这值不值得用AI来写”。有些代码是纯粹因为AI写起来快才用AI但如果这段代码难度不高、上下文又复杂AI往往写得不伦不类反而应该自己动手写个干净版本。可读性最高的代码有时候恰恰是不请AI代劳的代码。5. 维护阶段的长期策略让可读性不滑坡5.1 把代码规范沉淀成团队的“AI使用手册”维护阶段最大的挑战不是代码本身而是“每个人用AI的方式都不一样”。有的人会在提示词里写上完整的业务上下文生成出来的代码质量很高有的人让AI猜业务逻辑生成出来的代码跑通了功能却堆满了Magic Number。所以团队要想在维护阶段不崩溃最好的办法不是靠某个人自觉而是把AI代码生成的规范固定成一份文档。我们团队现在有一份《AI代码生成使用手册》里面包括提示词模板就是我上面分享的那套做了团队定制禁止事项列表比如禁止生成超过30行的函数、禁止使用魔法数字代码提交前的本地检查流程Lint 格式化 自己先读一遍代码评审中针对AI生成代码的追加要求这张文档最大的价值是让新人也知道“用AI写代码”不是写出来就算完而是跟正常写代码一样的标准要能被同事读懂才叫交付。5.2 让AI学习你项目的“领域词汇”和“架构约定”维护阶段还有一个更高阶的做法如果你用的是支持项目上下文或自定义指令的编程工具可以把项目的领域词汇表和架构约定注入进去。比如你们的项目里有order、invoice、refund这些领域实体你希望它们在代码里保持固定命名不希望AI突然改叫purchase_record或reversal_entry。做法也不复杂把下面这段内容加到你的AI配置里本项目的领域名词与约定 - 订单实体统一命名 Order禁止使用 Purchase 或 Record - 金额累计逻辑统一走 AmountCalculator 类禁止到处手写累加 - 所有配置读取必须经过 ConfigService禁止直接读取环境变量 - 错误处理统一抛 BusinessException禁止使用裸 raise这样做有三个明显好处第一AI生成的代码在一个周期内和人类代码的融合度高第二新同学接手时可以在代码里看到统一的领域概念而不是在order和purchase之间来回猜第三代码库的架构边界被AI自动遵守了维护时不会出现“一个模块突然绕过服务层直连数据库”这种结构性腐化。我自己实际操作下来的体会是想让AI生成的代码变得好读真正的重点不在“让AI写得更好”而在“把AI能读懂和遵守的标准建好”。这套标准花不了多少时间但它会把编码效率的红利真正变成团队资产而不是在代码库里留下一堆只有本人和AI能看懂的烂摊子。最后再分享一个小技巧每次生成完代码你自己默读一遍凡是需要停顿或回看的行就是可读性需要修补的地方。这不光适用于AI生成代码也适用于所有要交给别人的代码。读起来顺畅的代码维护起来才顺畅。