1. 从报名那一刻起,我就知道这不会是一次轻松的体验
1.1 为什么我会写一份“新生赛自述”
打开比赛报名表的时候,我犹豫了大概十分钟。倒不是担心拿不到名次——我这种刚把for循环写顺手的水平,本来也不敢想名次——真正让我犹豫的是另一个问题:如果只是体验一下,比完就散了,我还能留下什么?后来我给自己定了个规矩:从报名到比赛,整个过程必须写下来,能写多少写多少。于是就有了你现在看到的这篇,标题挂着【自述】,后面还加了“更新中”。
这段自述其实没有任何排版上的讲究,我只是想要大一这一年留下的东西不只有一张成绩单,还有我自己到底在想什么、卡在什么地方、后来是怎么一步一步往前挪的。如果你也是第一次参加新生赛,或者是班群里那种“要不卷一下试试”的选手,这篇记录也许会帮你提前看清赛道长什么样:不只是题目难不难,还包括备赛一个月大概要投入多少时间,比赛当天会不会紧张到读不进去题,以及赛后怎么复盘才算真没有白比。
1.2 为什么是“更新中”,而不是一篇大总结
我最怕读那种“岁月静好”式复盘文章:比赛结束、拿奖、感谢老师、继续努力,一气呵成。但真实过程根本不是这样。我比赛前一周还在为一道字符串题烦躁,比赛过程中有接近一小时处于自我怀疑状态,赛后头两天甚至不太想碰题库。这些乱糟糟的细节,反而是最值得记录的东西。所以我坚持用“更新中”来命名:事情没结束,水平还在变,与其写成一份定了稿的回忆录,不如当成一条持续有补丁的开发日志。
这种写法还有一个非常实际的作用:用一个公开系列倒逼自己投入。每次想偷懒的时候我就想,这周要是又不更新,下一次比赛前“自述”就要断更了。过去一个多月,我就是靠这个心理撑住每周训练量的。你不一定需要把记录发出来,但给自己拉一条时间线,哪怕只是在备忘录里随手记几笔,也会让备赛过程变得更有方向。很多时候,写下“今天没练”这句话本身,就比练习更让人清醒。
1.3 这篇自述适合谁,读完能拿什么
简单说,适合三类人。第一类是已经在报名表边缘犹豫的大一新生,你可以把它当一份真实的前线情报,看看要付多少时间成本;第二类是备赛过程中容易自我怀疑的人,你会看到一个同样菜过的人怎么不慌不忙地往前蹭;第三类是打算把“新生赛”写成故事的写作者,这篇记录里提到的时间线、失误细节和心路历程,可以作为你构建角色的素材库。
我想做的从不是把某一次失败或成功包装成热血爽文,而是诚实地记录:一场新生赛如何逼出一个新手身上的全部短板。你可能在比赛里遇到和我完全不同的题,但那些焦虑、卡壳、反反复复试错的感觉是共通的。能提前知道这些感觉会发生,本身就是一种储备。
2. 备赛六周,我踩过的每一块石头都被写进了笔记
2.1 我的真实起点:别被“大一新生”四个字骗了
学院新生群里总有人问,新生赛是不是给高中搞过竞赛的人准备的。我的答案是不完全是,但差距真实存在。我高中的信息课基本停留在打字练习,大学的C语言课进度又平缓。报名时我的水平大概是:会写变量、分支、循环,能看懂数组,知道函数要有返回类型,但一遇到“多组输入”就要翻半天课件。最尴尬的是有一天调试了半小时,最后发现自己只是把输出字符的大小写搞反了。
这里想给刚站到起点的你划第一个重点:知道得少不可怕,可怕的是用一句“我不会”就给自己判了出局。新生赛的题目设计通常照顾刚学过一个学期的学生,签到题基本都是简单模拟和数学计算,真正决定排名上限的,往往不是你能不能全AC,而是你会不会在中等难度的题上稳定拿分。赛后我看了一眼榜单上部,发现拿高分的人里至少有一半不是竞赛出身,他们只是比我更早开始练,也比我更稳定地练下去。
2.2 六个星期,我给自己排了一张训练表
比赛在周六上午,我提前一个半月决定报名。第一周只做一件事:把语法漏洞补齐;第二周用简单题练基本功;第三、四周刷模拟和枚举;第五、六周才敢碰二分、贪心、前缀和这类看起来像“算法”的东西。下面这张表当时贴在宿舍墙上,也和室友共享了一份:
| 训练区间 | 训练主题 | 题目类型 | 每周安排 |
|---|---|---|---|
| 第1-2周 | 语法补漏 | 输入输出、循环、数组、字符串基础 | 周一、三、五晚上各1小时 |
| 第3-4周 | 简单题形成手感 | 模拟、排序、枚举 | 周二、四各1.5小时,周六一下午 |
| 第5-6周 | 专项突破 | 二分、贪心、前缀和、简单动规 | 每天1题,周六一场2小时模拟赛 |
这张表看起来很常规,执行起来比想象中难很多。第一周的“语法补漏”不是重看教材,而是把所有例题重新敲一遍,每道题都要求编译一次性通过。听起来很笨,但它把我的赛场心理下限拉高了:至少不会因为连main函数都写错而当场慌神。
第三周我开始用OJ的“入门”标签刷题,每天做完题后把题解和自己的思路对一遍,再用自己的话写进笔记。这个习惯让比赛前我就见过了十几类常见题型的套路。第五周开始记录做题时间:简单题超过20分钟就停下来,问自己到底是读题慢、思路不清,还是代码实现有问题。这个过程比多刷十道题更有用。每晚保存记录的时候,我能清楚看到自己今天比昨天多稳住了几道题,也能看到哪些知识点只是“见过”,并没有真正变成手速。
2.3 资料选择:我踩过的三个坑
第一个坑叫收藏夹积灰。我一开始收藏了很多算法书,结果两周时间只读完第一章。后来我换成“按标签刷题”的思路:选一个稳定可用的在线评测系统,从“入门”标签开始,每天只做一道看得懂题解的题,并且强制复述题解。初期最重要的不是知识面的宽度,而是连续完成的长度,正反馈才是新手坚持下去的真正燃料。
第二个坑叫“看题解等于会做”。我有一阵每次看不懂就直接点开题解,复制过去就跑,结果比赛前一周发现,换一道类似的题我还是没有思路。后来我改成:看题解只看思路提示,然后合上题解,自己把代码从零敲出来。哪怕最终代码长得和题解一样,肌肉记忆也是自己的。
第三个坑是忽视数据范围。新生赛的题很爱用超过int范围的数据做陷阱,我赛前第一次被long long问题卡住时整个人都懵了。从那以后,只要题目里出现10^9这种量级,我就会默认使用long long。多组输入也很常见,从最简单的情况开始就要养成模板习惯:
#include <bits/stdc++.h> using namespace std; int main() { ios::sync_with_stdio(false); cin.tie(nullptr); long long a, b; while (cin >> a >> b) { cout << a + b << '\n'; } return 0; }这里多说一句,为什么很多人不写这两句加速代码:cin默认会和C语言的scanf输入流保持同步,导致读入变慢。做新生赛时题目数据规模可能不大,但养成这个习惯,以后打正式一点的比赛就不会在输入输出上多花几倍时间。这段代码也是我赛前唯一会默写的“模板”。
3. 比赛当天:三小时浓缩成的时间线、压力和多次推倒重来
3.1 开赛前的十分钟,我没在背模板
比赛那天上午,我提前三十分钟到机房。大半选手都在低头翻自己的小本子,我也翻出了一个小本子,但上面记的不是模板,而是三条提醒:第一,先读题,别急着写;第二,每道题交之前都先算一遍极端数据;第三,如果卡住超过半小时,就起来走一圈。这三条是我赛前给自己定的“应急处置手册”。事实证明,它们比任何模板都救命。赛前背模板当然有意义,但如果把临场精力花在回忆模板上,反而容易忽略真正重要的题目理解。
入场之后我还做了一件事:把每道题可能在哪个知识点方向上挨个扫了一遍,顺便确认了题目页面的字体、编译器和提交按钮的位置。这些细琐的准备看起来没用,却能极大减少赛场上的“意外感”。比赛真正考验的往往不是你会多少东西,而是你在紧张状态下能把多少平时发挥出来。我还给键盘上贴了张便利贴,写的是“先看数据范围”,因为这是我赛前犯过最多的低级错误。
3.2 前90分钟:从签到题写成了过山车
比赛正式开始以后,我没有从第一题开始一路做到底,而是先把八道题从头到尾快速翻一遍,再回到最前面开始做。A题是一道很基础的整数幂次判断,我五分钟写完交上去,却等来一个红色的错误提示。那一瞬间大脑是空白的,后来才发现题目里包含0次方特判,循环写法如果不单独处理就会出错。改掉这个小坑之后,终于拿到了熟悉的绿色反馈。开赛二十分钟,我的收获很明确:看得懂题目不等于想得全边界。
接下来的B题和C题比A题难度大一点。B题是排序后的相邻差值,C题是日期合法性判断。日期题最折磨,因为需要同时判断闰年、大小月、二月的最后一天,流程一多就容易改出新的bug。我大概重写了三版,最终在提交之前手动加了四个测试样例才敢交。那次经历让我彻底记住一件事:手造样例永远比事后拍大腿有用。比赛不是靠祈祷,而是靠验证。
那段时间心态很像坐过山车:每看到一次Accepted就想欢呼,每次看到红色反例又觉得嘴里的零食都不香了。但说实话,我最惊喜的不是AC的数量,而是自己终于能做到“每一份代码提交前都被验证过”。对新手来说,这本身就是从“随便写写”到“认真对待”的分水岭。
3.3 90分钟后:当心态开始塌方,我把目标从“AC”改成“拿分”
比赛过半,我面前还剩好几道题,时间剩得不多。E题是一道典型的贪心,我盯着看了十分钟,完全不知道从哪下手。那一刻我做的第一件事不是硬刚,而是强迫自己把手放在键盘上停下,然后做了个决定:先不碰E,转头去看F。F题的包装复杂,但剥掉壳之后其实是个二维前缀和,因为我知道这个知识点,所以慢慢写出了一个可以跑小数据范围的代码,拿到部分分。
这里想认真说一句:新生赛并不要求每道题都全对。很多题目会按数据点给部分分,能拿到的部分分加起来,往往已经足够让排名变得好看。不要被“AC”这个念头绑架,先抢分,再谈全对,这是比赛中后期最重要的策略转变。那天我最后的成绩算不上耀眼,但能坚持到最后一刻的原因,恰恰是中途放弃了“全都会”的执念。
把比赛时间线整理出来会更清楚:
| 比赛时间 | 我在做什么 |
|---|---|
| 0-18分钟 | 快速翻题,攻克A题,处理0次方特判后AC |
| 18-45分钟 | B题AC,C题第一次WA,标记待回看 |
| 45-90分钟 | C题重写第三版并AC,D题漏看“字典序”只拿部分分 |
| 90-150分钟 | E题卡住,转F题用二维前缀和拿部分分 |
| 150-180分钟 | G题尝试暴力枚举,稳定拿到前三组小样例分 |
4. 赛后复盘拿到的不是奖状,而是一份“问题清单”
4.1 把比赛过程摊开来看
比赛结束,系统出了排名。名次比我来之前预想的好,但远没到可以骄傲的程度。真正有价值的部分是把每道题的状态拉出来重新看一遍,因为我发现日常训练里完全看不到的问题,在比赛中全暴露了。
| 题号 | 预估难度 | 尝试次数 | 最终状态 | 暴露出的问题 |
|---|---|---|---|---|
| A | 简单 | 3次 | Accepted | 边界特判不全,0次方漏掉 |
| B | 简单 | 1次 | Accepted | 多组输入模板已掌握 |
| C | 中等 | 3次 | Accepted | 逻辑分支太绕,重构后才稳定 |
| D | 中等 | 1次 | 部分分 | 题目里的“字典序”要求被漏读 |
| E | 较难 | 0次 | 未提交 | 贪心模型套不上场景 |
| F | 中等 | 2次 | 部分分 | 时间不足,且被E题打乱节奏 |
| G | 较难 | 1次 | 部分分 | 暴力枚举只拿小数据分 |
| H | 较难 | 0次 | 未提交 | 时间耗尽,基本没看 |
这张表让我看见了训练方式的缺陷。我平时刷题喜欢“会做了就下一道”,从不记录自己究竟卡在读题、卡在建模还是卡在输出;比赛一旦紧张,这些缺陷会全部叠加在一起爆发。赛后复盘最有价值的产出,不是记住某道题怎么做,而是知道自己下次该往哪里使劲。对我来说,这份问题清单比名次更能刺激我继续训练。
4.2 三个必须写进笔记的根因
第一个根因是读题习惯。D题题干里有一句“如果多组答案,输出字典序最小的”,我用眼睛扫过去了,结果代码实现里连字典序这个概念都没出现。错失这几分之后,我给自己定了新规矩:每次动笔之前,用自己的话把题目复述一遍,特别是带限制条件的小字部分。这个习惯后来也救过我很多次,因为很多“隐藏条件”就藏在你根本不会回头看的位置。
第二个根因是模型迁移能力。E题的贪心模型我在训练里确实见过,只是题目换了一层生活化包装,我就不敢往下写。后来我给自己设计了一个“一句话归档法”:每做完一道题,必须用一句话概括它考的是什么模型,比如“这个题是区间选点的变体”。积累足够多模型后,比赛时看到新题的第一反应就会从“没见过”变成“长得像谁”。
第三个根因是时间分配。我在A题和C题上花的时间明显超标,导致后半程缺少整块时间去啃真正能拉开差距的题。这个问题的解法不是“下次快一点”,而是赛前先做目标规划:哪几道题必须拿满,哪几道题只用部分分保底,剩下时间集中打哪一道。有了这个计划,比赛时就不会被一道题拖死。
4.3 “更新中”的第一步:把问题清单变成训练计划
既然叫“更新中”,复盘就不能只是一篇总结。我在赛后第三天把这些结论转成了下一阶段的训练安排:
- 每周一、三:读题训练,每道题先复述题意再动手,训练识别题干里的隐藏条件。
- 每周二、四:模型归纳训练,刷题时强制写下题型标签,并归并到自己的“一句话归档”笔记里。
- 每周六上午:全真模拟两小时,严格使用比赛同样的时限、工具和评分规则。
- 每次模拟赛后更新一段记录,内容包括做题用时、卡住点、情绪波动和下一次要修的地方。
这个过程就像游戏存档:你每次复盘都会生成一个新的存档点,下次训练直接从存档点继续,而不是每次从零开始。保持这个循环,比赛前疯狂刷五十道题更容易带来真正的变化。而且这种“复盘-转化-再复盘”的节奏,会让你慢慢从被动做题变成主动管理自己的学习进度。
5. 给下一届新生的几条实在建议,以及我接下来要更新的方向
5.1 如果能回到报名前一天,我会提前知道四件事
第一件事:先保证拿分,再追求AC。新生赛一定有送分题,也一定有拉开差距的难题。把送分题稳稳拿住,学会用部分分去薅中等题的分数,远远好过死磕一道自己搞不定的难题。我这次最大的进步,就是接受自己不是上来就能“全都会”的人。想清楚这一点后,比赛每一分钟都花得更值了。
第二件事:备赛时就要按真实比赛环境训练。我一开始刷题时不断网、不限制时间,导致比赛现场看到计时器就莫名焦虑。后来每周六安排一次完整模拟赛,中途不许暂停、不许查资料,两小时准时收卷,这种感觉很快就被脱敏了。模拟赛的分数不重要,重要的是把你的比赛节奏练出来。你会在模拟赛里提前发现“原来自己第40分钟会饿”“原来第90分钟会坐立不安”,这些都属于比赛的一部分。
第三件事:留一份自己的错题本,而不只是收藏别人的题解。错题本不要求工整,但每一条至少要写清楚三块:当时为什么错、正确思路是什么、以后怎么避免。这份笔记不是给别人看的,它是你比赛前一晚最踏实的复习资料。比赛前翻错题本比临时刷题更容易入脑,因为每条都是你自己踩过的真实教训。
第四件事:提交之前手造几个边界样例。题目给的样例只是最低保障,真正容易翻车的地方是数组越界、空输入、数据最大或最小这些边界情况。每次多花两分钟造几个样例验证,你的WA数量会肉眼可见地减少。别人在赛后懊恼“当时怎么没想到”,你在赛中就已经把这条路堵死了.
5.2 接下来,我打算让这篇自述怎么往前走
比赛并没有成为我学习编程之路的终点。当前我的进度是:每周保持两场模拟训练,整理一份不断变厚的错题本,并把新生赛暴露出的每一项问题逐条勾掉。下一次更新大概率会以“新生赛【自述,更新中:第二个月】”的形式出现,里面会有我的新训练记录、又一次模拟赛的事故现场,以及我继续踩到的新坑。你如果感兴趣,可以把它当成一档持续更新的存档连载来看。
我会在每个周六晚上固定打开这个文档,把本周的训练数据、心态变化、做题记录都追加进去。更新内容不会太长,但会一直保持真实。如果某周我偷懒了,我也只会如实写上“这周只练了两天”,不会假装自己很勤奋。因为自述的意义本来就不是表演,而是让未来的自己看到真实轨迹。
最后想对准备报名下一场比赛的朋友说一句:如果这篇自述里有一句话值得带走,大概是“现在就记录”。记录你此刻有多菜,一点都不丢人,重要的是让一个月后的自己看见变化。我在写这个系列的时候,也一直在等这个变化。下一次更新,我们场上见。