Cursor越用越蠢?问题不在AI,在你不懂上下文管理
我用 Cursor 三个月,项目从 500 行涨到 5000 行,AI 却越来越蠢了
上周三凌晨两点,我看着 Cursor 给我生成的第 47 行完全无关的代码,突然意识到一个问题:不是 AI 变笨了,是我的上下文管理烂得像屎山。
三个月前我刚切到 Cursor 时,感觉自己像钢铁侠附体。Tab 补全跟读心术似的,Ctrl+K 改代码比我老婆还懂我。项目突破 3000 行之后,这玩意儿开始给我推荐一些我三天前就删掉的函数,还一脸自信。
我差点就发朋友圈骂 Cursor 割韭菜了。直到在 GitHub Issues 里刷到一个老哥的评论:
"Cursor's context window isn't magic. It's a hungry beast, and you're feeding it garbage."
翻译成人话:上下文窗口是有限的,你塞进去的每一行屎,都会挤掉一行黄金。
那个让我破防的 .cursorrules 文件
先说个智商税。
2024 年 11 月我刚入坑那会儿,刷到某博主的"史上最强 .cursorrules 配置",脑子一热就复制了一个 300 行的规则文件。里面详细到变态——项目架构、命名规范、甚至教 AI "像资深架构师一样思考"。
猜猜结果?
Cursor 的补全延迟从 200ms 飙升到 2 秒多,生成的代码反而更离谱了——它开始把 React 组件写成 Vue 的语法。对,你没看错。因为我的规则文件里同时提到了两个框架。
后来翻 Cursor 的文档(对,RTFM 永远是对的),才发现一个关键信息:
Cursor 的上下文窗口大概 8000-10000 token,而且你的 .cursorrules 文件会永久占着这个窗口。
我的 300 行规则文件,光它一个就吃了快 2000 token。剩下 6000 token 要分给当前文件、相关文件、对话历史。AI 不精神分裂才怪。
现在的我,.cursorrules 只有 8 行:
你是一个 TypeScript + React 专家。
使用函数组件和 Hooks。
状态管理用 Zustand。
样式用 Tailwind CSS。
不要使用 any 类型。
优先使用 async/await。规则越少,AI 越聪明。 这不是玄学,是 token 数学。
长项目不卡顿的三个野路子
嗯...这个比较 tricky。
踩了三个月坑,我总结出三招。官方文档里找不到,都是实战撞出来的。有几个甚至跟市面上的"最佳实践"完全反着来。
1. 给项目做"分区手术"
我那个项目是个 SaaS 后台,有用户管理、数据分析、支付三个模块。以前我喜欢一个 Chat 聊到底,从登录逻辑问到图表配置。
然后 Cursor 就开始"串台"——给支付模块生成用户管理的代码,引用的函数横跨三个不同文件,没一个对的。
现在的做法:每个功能模块开独立 Composer。
具体操作:
- 项目根目录建 `.cursor/contexts/` 文件夹
- 每个模块写一个 `.context.md` 文件,只描述本模块的核心文件和依赖
- 切换任务时,用 `@context` 命令加载对应上下文
比如我的 payment.context.md:
# 支付模块上下文
核心文件:
- src/features/payment/PaymentForm.tsx
- src/features/payment/useStripe.ts
- src/lib/stripe.ts
外部依赖:
- src/lib/api.ts (只用 createPaymentIntent 函数)
- src/store/userStore.ts (只读 currentUser.id)
不要引用:
- src/features/analytics/ (数据分析模块)
- src/features/users/ (用户管理模块)这个文件不到 100 行,但让 Cursor 的准确率从"随机数生成器"变成了勉强能用的代码。
等等,这里我要更正一下——不是勉强能用,是能直接跑的代码。差别很大。
原理很简单:你明确告诉 AI 不要看什么,比告诉它看什么重要得多。
2. 对话历史的"断舍离"
Cursor 的 Chat 历史会持续吃上下文窗口。聊了 50 轮之后,AI 已经彻底忘了你最初的需求。
我说个血泪教训:有一次让 Cursor 重构一个表单组件,前 20 轮很顺利,后面它开始"创新"——给我加了一堆根本不存在的业务逻辑,什么"根据用户地理位置自动切换货币单位"。
我根本没提过这个需求。
因为早期的对话被挤出窗口了,它已经不记得这个表单是干嘛的,开始自由发挥了。
现在的做法:每 15-20 轮对话,主动重置上下文。
不是关掉重开,而是:
1. 把当前的关键决策和接口定义复制到一个临时文件
2. 用 @file 命令重新加载这个文件
3. 在新 Chat 里说:"基于这个文件继续工作"
这就像 Git 的 squash commit,把 20 个零散的操作压成一个清晰的 snapshot。
我自己统计过(数据量不大,就 30 多次测试),重置后的前 10 轮对话,代码生成准确率能回到 90% 以上。不重置的话,30 轮后准确率掉到 60% 以下,有时候甚至更低。
3. 文件引用的"少即是多"
Cursor 的 @file 和 @folder 功能确实好用,但也是双刃剑。
有一次我图省事,直接 @folder src 把整个项目喂给 AI。结果它开始"博览群书"——生成的代码引用了 6 个月前的废弃工具函数,因为那个文件还躺在 src 里没删。
报错信息我还记得:
Cannot find module '../../utils/deprecated/oldFormatter'我找了 20 分钟才发现是 AI 给我引错了文件。
Cursor 不会判断文件的新旧和相关性,它只会忠实地读你喂给它的一切。
现在的原则:
- 只引用**当前任务直接相关**的 2-3 个文件
- 函数签名复杂的话,单独复制函数签名,别拉整个文件
- 用 `@file:line_start-line_end` 只引用关键代码段
比如要改一个 API 调用,我只引用:
- 当前组件文件(我要改的地方)
- API 路由文件的目标函数签名(`@file:api/users.ts:45-52`)
- 类型定义文件的相关 interface(`@file:types/user.ts:10-25`)
三个文件,总共不到 200 行代码。AI 的响应速度快了大概 3 倍,生成的代码也准多了。
一个反直觉的发现
你可能会想:"那我直接上 Claude 3.5 Sonnet 的 API,上下文窗口 200K,不就能随便喂了?"
我也这么想过。
花了整个周末(2025 年 1 月中旬,我记得特别清楚,因为周日晚上还通宵了)接入 Cursor 的 API 配置,切到 200K 窗口的模型。
结果?
更差了。
因为窗口越大,AI 的"注意力"越分散。 就像让你在图书馆里找一本书,告诉你"在第三排书架上"和"在这个图书馆里",前者你 30 秒找到,后者你找一整天。
200K 窗口的模型,生成代码时会"考虑"更多无关信息,反而容易过度设计。一个简单的 CRUD 接口,它给我生成了带缓存、重试、熔断、降级的"企业级方案"——大哥,我在做个人项目啊,我就想存个用户信息。
据我了解,这个问题在 2024 年底的一些技术博客里也有提到,RAG 领域管这个叫"检索噪声"。
上下文管理的本质不是"塞更多",而是"塞更准"。
我的日常操作流(可直接抄)
现在我的 Cursor 工作流长这样:
开始新功能前:
1. 创建一个 .context.md 文件(不超过 50 行)
2. 在 Composer 里 @context 加载它
3. 只引用 2-3 个核心文件
开发过程中:
1. 每 15 轮对话,主动总结当前状态
2. 把关键决策写进 .context.md
3. 重置对话,重新加载上下文
遇到卡顿/错误时:
1. 检查是不是引用了太多文件(超过 5 个就太多了)
2. 检查 .cursorrules 是不是超过 20 行
3. 检查对话历史是不是超过 30 轮
项目规模变大时:
1. 按模块拆分 .context.md
2. 每个模块独立 Composer
3. 跨模块逻辑用明确的接口文档,别让 AI 自己猜
最后说点得罪人的话
市面上的 Cursor 教程都在教"怎么写更好的 Prompt",但好像没人告诉你:Prompt 工程的天花板,是你对上下文窗口的理解。
就像你给实习生布置任务。
给他看 3 页相关文档,做得很好。给他看 300 页整个项目的文档,反而懵了。
AI 也是这个道理。它不是神,就是个读了你上下文然后猜你想要什么的概率模型。我觉得这个理解还挺重要的。
你喂得越精准,它猜得越准。你喂得越多,它猜得越离谱。
现在我的项目 5000+ 行,Cursor 的响应速度和准确率跟 500 行时差不多。不是 AI 进步了。
是我终于学会了闭嘴。
你在用 Cursor 时遇到过什么离谱的补全?有没有什么独家的上下文管理技巧?评论区教教我,真的很需要。
相关阅读:
- [为什么你的 AI 编程助手越来越蠢?——上下文污染的真相](#)
- [Cursor vs Copilot:六个月深度对比,我选第三个](#)
- [从 0 到 10000 行:一个独立开发者的 AI 协作指南](#)
#Cursor #上下文管理 #AI编程 #开发效率 #避坑指南 #独立开发
读者评论 5