从恐惧到依赖:我用AI写代码和调试的真实体验与技巧

2026/05/02 AI 共 4367 字,约 13 分钟

从恐惧到依赖:我用AI写代码和调试的真实体验与技巧

引言

还记得第一次尝试用AI写代码时的场景吗?我当时的体验是:生成一段看起来完美的代码,结果一运行就报错,然后花了比手写多两倍的时间去修复。这种“鸡肋”感让很多开发者对AI编程工具敬而远之。

然而,仅仅半年后,我的日常工作已经离不开AI了。从编写单元测试到调试棘手的并发Bug,AI成为了我最得力的“结对编程伙伴”。本文将分享我在这段时间积累的实战经验,包括如何让AI写出可用的代码、如何利用它进行高效调试,以及必须避开的坑。

一、AI写代码:不只是“复制粘贴”

很多人把AI写代码等同于“让AI生成一段代码,然后直接复制到项目中”。这是最大的误区。高质量的AI辅助编程更像是一个迭代的协作过程

1.1 从模糊需求到精确指令

AI无法读取你的大脑,它只能理解你输入的提示词。一个模糊的提示如“写一个排序算法”和“用Python写一个针对大型数据集的快速排序,要求原地排序且时间复杂度为O(n log n)”得到的结果天差地别。

实战案例:生成一个REST API端点

假设我们需要一个用户注册接口。新手可能会这样问:

写一个用户注册的API

AI生成的代码往往缺乏错误处理、输入验证和安全性考虑。而经验丰富的开发者会这样分解任务:

  1. 定义数据模型:先让AI生成User模型(包含用户名、邮箱、密码哈希等字段)。
  2. 生成业务逻辑:要求AI实现密码加密、邮箱格式验证、用户名唯一性检查。
  3. 生成控制器:最后组装成完整的POST /api/register端点。

示例提示词(分步骤):

第一步:用Python和FastAPI创建一个User数据模型,包含username(字符串,唯一)、email(字符串,格式验证)、password_hash(字符串,存储bcrypt哈希值)。
第二步:编写一个函数register_user(db: Session, user: UserCreate),实现以下逻辑:
- 检查邮箱是否已被注册
- 检查用户名是否已被占用
- 使用bcrypt对密码进行哈希
- 将新用户写入数据库
第三步:基于以上函数,创建一个POST /api/register端点,返回201状态码和用户信息(不包含密码哈希)。

AI输出示例(部分):

from fastapi import FastAPI, HTTPException, Depends
from sqlalchemy.orm import Session
import bcrypt

# ... 模型定义 ...

def register_user(db: Session, user: UserCreate):
    # 检查邮箱是否存在
    existing_email = db.query(User).filter(User.email == user.email).first()
    if existing_email:
        raise HTTPException(status_code=400, detail="Email already registered")
    
    # 检查用户名是否存在
    existing_username = db.query(User).filter(User.username == user.username).first()
    if existing_username:
        raise HTTPException(status_code=400, detail="Username already taken")
    
    # 密码哈希
    hashed_password = bcrypt.hashpw(user.password.encode('utf-8'), bcrypt.gensalt())
    
    # 创建用户
    db_user = User(username=user.username, email=user.email, password_hash=hashed_password)
    db.add(db_user)
    db.commit()
    db.refresh(db_user)
    return db_user

关键点:通过拆解需求、提供上下文(如数据库Session、返回格式),AI生成的代码几乎可以直接集成到项目中,仅需微调。

1.2 代码补全 vs. 代码生成

GitHub Copilot这类工具擅长代码补全,而ChatGPT更适合代码生成。理解这两者的区别很重要:

  • 代码补全:你写一个函数签名,AI帮你填充函数体。适合已知模式的重复性工作,如CRUD操作、数据转换。
  • 代码生成:你描述一个功能,AI从零生成完整代码块。适合探索新库、编写测试用例或生成配置代码。

小技巧:在Copilot中,如果你觉得补全不够准确,可以尝试先写一段详细注释,再回车触发补全。注释就是你的提示词。

二、AI调试:从“黑盒”到“透明”

调试是AI最被低估的能力。传统调试依赖断点和日志,而AI可以帮你进行静态代码分析错误根因推理

2.1 错误信息的“翻译官”

当遇到一个看不懂的错误堆栈时,直接把错误信息丢给AI是最快的解决方式。

真实场景:一个Python项目中遇到了RecursionError: maximum recursion depth exceeded

我的提示词

我有以下Python代码(粘贴代码),运行时抛出RecursionError。请分析为什么会出现无限递归,并给出修复方案。注意:代码中使用了装饰器@lru_cache。

AI分析: AI指出,虽然使用了@lru_cache,但递归函数中有一个参数是可变对象(如列表),导致缓存失效,每次调用都重新计算,从而触发递归深度限制。修复方案是将可变参数转换为不可变元组。

关键点:AI不仅指出了错误,还解释了为什么缓存失效,这是传统调试器无法做到的。

2.2 单元测试的“自动生成器”

编写单元测试往往比写业务代码更耗时。AI可以极大地加速这一过程。

示例:为上述register_user函数生成测试

提示词

为以下register_user函数编写pytest单元测试。要求:
1. 测试正常注册流程
2. 测试重复邮箱注册
3. 测试重复用户名注册
4. 使用unittest.mock模拟数据库Session

AI输出

import pytest
from unittest.mock import MagicMock, patch
from your_module import register_user, UserCreate

def test_register_user_success():
    # 模拟数据库
    db = MagicMock()
    db.query.return_value.filter.return_value.first.return_value = None
    
    user_data = UserCreate(username="testuser", email="test@example.com", password="securepassword")
    
    result = register_user(db, user_data)
    
    # 验证用户被添加
    db.add.assert_called_once()
    db.commit.assert_called_once()
    assert result.username == "testuser"

def test_register_user_duplicate_email():
    db = MagicMock()
    # 模拟已存在的邮箱
    db.query.return_value.filter.return_value.first.side_effect = [MagicMock(), None]
    
    user_data = UserCreate(username="testuser2", email="existing@example.com", password="pass")
    
    with pytest.raises(HTTPException) as exc:
        register_user(db, user_data)
    assert exc.value.status_code == 400

经验:AI生成的测试通常覆盖了主要路径,但边界条件(如超长用户名、空密码)需要手动补充。把AI生成的测试作为起点,然后根据业务逻辑增强。

三、必须避开的陷阱

3.1 幻觉问题:AI会“编造”不存在的API

这是最危险的陷阱。AI可能会为你生成一个看似合理的函数调用,但实际上该函数并不存在。例如,让AI写一段使用某个第三方库的代码,它可能“发明”一个方便但不存在的方法。

解决方案

  • 交叉验证:对于不熟悉的库,让AI生成代码后,一定要查阅官方文档确认API是否存在。
  • “请提供文档链接”:在提示词中要求AI提供官方文档引用,虽然AI可能也会编造链接,但至少会促使它生成更准确的代码。

3.2 安全漏洞:AI不关心你的安全

AI生成的代码通常关注功能实现,而忽略安全性。例如,它可能会生成直接拼接SQL字符串的代码(SQL注入风险),或者将密钥硬编码在代码中。

最佳实践

  • 永远不要直接使用AI生成的密码学或认证代码,除非你完全理解其原理。
  • 在提示词中明确要求:“请使用参数化查询防止SQL注入”或“请使用环境变量管理密钥”。

3.3 上下文丢失:长对话中的“失忆”

在长时间对话中,AI可能会忘记之前的约定。例如,你定义了项目使用SQLAlchemy,但后续让它生成代码时,它可能突然使用Django ORM。

解决方案

  • 定期总结上下文:每几轮对话后,主动总结当前使用的库、框架和约定,让AI确认。
  • 使用系统提示:在ChatGPT中,可以在对话开始前设置系统角色,例如:“你是一个精通FastAPI和SQLAlchemy的Python开发者,所有代码必须包含类型注解和错误处理。”

四、进阶技巧:让AI成为你的“私人导师”

除了写代码和调试,AI还可以帮助你学习新技术。

场景:学习Kubernetes的Service Mesh。

提示词

我是一名有5年经验的Java后端开发者,但完全不懂Service Mesh。请用类比的方式解释Istio的核心概念(如Sidecar、VirtualService、DestinationRule),并给出一个微服务A调用微服务B时流量如何被拦截和路由的流程图描述。最后,提供一个简单的YAML配置示例,实现灰度发布。

这种“教学式”提示词,可以让AI根据你的知识水平调整解释深度,比阅读官方文档更高效。

结语

AI写代码和调试并不是要取代开发者,而是将我们从繁琐的重复劳动中解放出来,让我们能专注于架构设计、业务理解和创新。掌握与AI协作的技巧——精确的提示词、分步拆解、交叉验证——是未来开发者必备的核心竞争力。

下次当你面对一个空白的编辑器时,不妨先问问AI:“如果我要实现这个功能,最好的代码结构应该是什么?”你会发现,从恐惧到依赖,只需要一段高质量提示词的距离。

文档信息

Search

    Table of Contents