Go 后端转 AI:非科班怎么补?一张 3 列路线表(可保存)

一、先把那场模拟面试写出来

前几天一位读者给我留言,说他不是科班出身,做 Go 后端一年多,现在想往 AI 上靠,最怕别人问的一句话是「你这些是按什么标准练的」。

他白天上班,晚上练。真正让他难受的不是练不动,是没人告诉他练到什么程度算够。

到这一句,回答往往就停住了。停住的时间不长,三五秒,但这几秒足够让面试官把你的水平往下降一档。

被问住的这位,硕士读的是土木和水利,毕业后先做了一年海外商务,后来才转的 Go 后端,再往 AI 上靠。他的简历项目是能讲的,代码也写得动,差的从来不是投入时长,也没人把这个岗位的标准当面给他拆过。

多数人把那句追问理解成「时间够不够」,于是答案就变成了再挤一点时间。可面试官问的不是投入量,是口径:你这几个月做的事,有没有一个别人也能核对的判据。有这个判据,两小时和八小时的区别只是进度快慢;没有它,练多久都停在同一个地方。

二、那句追问其实在问三件事

我把这句追问拆开复盘过很多次,它落在三个地方。

第一,你有没有外部口径。自己觉得掌握了不算数,得有一个不由你说了算的东西承认你掌握了。它可以是一次模拟面试的现场抽问,也可以是让别人照着你的项目代码实际跑一遍,唯独不能是你自己的感觉。

第二,补不动的时候你怎么判断。是方法错了,还是时间投得不够?这两种情况的处理路径完全相反。答不上来,说明你这段时间始终是线性地往前推,没有停下来区分过这两种暂停。

第三,别人问进度时你能不能拿出能被复算的数字。不能用「学了很多」这种表述,要说清楚上一轮被问住的那个问题现在清零了没有,还剩几个,剩的分别是哪几个。能被复算,意味着别人照着你的说法也能得到同一个结果。

这三件事里,第一件和第二件要提前写清楚,第三件适合交给工具。下面先说这三件事怎么落成一张能保存的表。

三、把「标准」落成一张三列表

我给这位同学用的是一张三列表,每列都有明确含义,抄下来贴墙上也行。

练什么 验收信号(十分钟能自验完) 谁来判
一条端到端的链路能跑通:从请求进来到结果落库,每一步指得出来 不看代码,能把这条链路从头顺一遍,中途被人打断三次还能接上 找一个没参与这个项目的人听一遍,他能复述出关键两步就算过
Agent 或 RAG 每一步对得上:切分、召回、重排、引用溯源各自负责什么 随手挑一步追问「为什么这样做」,三句话里给出取舍理由,而不是诉诸惯例 让别人拿着固定追问清单随机抽,不许提前知道抽哪条
简历上的每个数字说得出来源:怎么测的、改了什么把它拉动了多少 同一个数字换个问法(多大样本、多久测一次、排除过哪些干扰)还能答 模拟面试官当场挑一个数字往下追两层

这张表有三个使用细节。

一是第二列必须十分钟能验完。判断过程如果一天都执行不完,它在真实备战里就会被跳过,等于没写。

二是第三列不能写自己。「我自己再想一遍」不算验收人,验收人必须是能对你说「不行」的人,或者能独立复跑出同一结果的流程。

三是三类要轮着查,别只挑顺手的那类。第三类最容易被跳过,很多人大量时间花在前两类,最后倒在「你说提升了三成,这个数是按什么口径测的」这一句上。

四、他真正跑到位的那一步:变量不是时长

这位同学在职的时候,每天只能挤两小时;后来离职专心准备,拉到每天八小时。

时长涨了四倍。只看这个数,会得出完全错误的结论。

真正让他通过的是同一段时间里累计做完的十次内部模拟面试。每次结束之后,他会留下三类清单:被问住的、答得含糊的、数字说不清口径的。下一场开场之前,先把上一场的清单过一遍,没清零的旧问题不许被新问题覆盖掉。

时长是投入,模拟面试是节拍器。没有节拍器,投入再多也只是把同样的漏洞重复了更多遍。

这里有个容易算错的地方:十次不等于把同一套题做了十遍。每一轮的追问会换场景,唯一必须带过来的是上一轮没清零的那几个问题。如果把每次都当成重来,做到二十次也是原地打转。

五、把节拍器做成脚本,别靠记忆

上面这套流程靠人记会走样,落成一个脚本更稳。日志按行写,一行一条只有三个字段,依次是日期、状态、问题,用竖线隔开,同一个问题重复出现时以最后一次的状态为准。

python 复制代码
import re
import sys

# 训练日志:一行一条,格式「- 日期 | 状态 | 问题」
LINE_RE = re.compile(r'^\s*-\s*(\d{4}-\d{2}-\d{2})\s*\|\s*(被问住|已解决)\s*\|\s*(.+?)\s*$')


def parse(path):
    """按行读训练日志,同一个问题保留最后一次出现的状态。"""
    records = {}
    order = []
    days = set()
    with open(path, encoding='utf-8') as fh:
        for raw in fh:
            m = LINE_RE.match(raw)
            if not m:
                continue
            date, state, question = m.groups()
            days.add(date)
            if question not in records:
                records[question] = {'first': date, 'last': date, 'times': 0, 'state': state}
                order.append(question)
            item = records[question]
            item['last'] = date
            item['times'] += 1
            item['state'] = state
    return order, records, sorted(days)


def main():
    if len(sys.argv) != 2:
        print('用法: python train_report.py <日志路径>')
        return 1
    order, records, days = parse(sys.argv[1])
    if not records:
        print('没有读到有效记录,检查格式是不是「- 日期 | 状态 | 问题」')
        return 1

    lines = sum(v['times'] for v in records.values())
    pending = [q for q in order if records[q]['state'] == '被问住']
    cleared = [q for q in order if records[q]['state'] == '已解决']

    print('记录条数 %d(%s ~ %s,覆盖 %d 个练习日)' % (lines, days[0], days[-1], len(days)))
    print('问题总数 %d:已清零 %d 个,未清零 %d 个' % (len(order), len(cleared), len(pending)))
    print('清零率 %.1f%%' % (100.0 * len(cleared) / len(order)))
    print('')
    if pending:
        print('未清零清单:')
        for i, q in enumerate(pending, 1):
            v = records[q]
            print('  %d. %s(出现 %d 次,最近 %s)' % (i, q, v['times'], v['last']))
    else:
        print('未清零清单:空')
    return 0


if __name__ == '__main__':
    sys.exit(main())

下面是一份示例日志,全部是示例数据,不对应任何真实记录:

复制代码
# 训练日志(示例)

- 2026-08-03 | 被问住 | RAG 为什么按段落切分,不用固定长度
- 2026-08-03 | 被问住 | 召回率掉了先看哪一个数
- 2026-08-06 | 已解决 | RAG 为什么按段落切分,不用固定长度
- 2026-08-09 | 被问住 | 调用超时之后重试几次,间隔怎么定
- 2026-08-12 | 已解决 | 召回率掉了先看哪一个数
- 2026-08-15 | 被问住 | 简历上那个 P95 是怎么测出来的
- 2026-08-18 | 被问住 | 调用超时之后重试几次,间隔怎么定

跑出来的真实输出:

复制代码
记录条数 7(2026-08-03 ~ 2026-08-18,覆盖 6 个练习日)
问题总数 4:已清零 2 个,未清零 2 个
清零率 50.0%

未清零清单:
  1. 调用超时之后重试几次,间隔怎么定(出现 2 次,最近 2026-08-18)
  2. 简历上那个 P95 是怎么测出来的(出现 1 次,最近 2026-08-15)

这份报告里最该看的不是清零率,是「出现次数」这一列。第二个问题第二次出现在未清零清单里,说明它上一次压根没被解决,只是又撞了一次;第一个问题只出现一次,属于新账,处理顺序排在它后面。

这份输出和第二节那三件事的对应关系也值得记下来:清零率回答的是能不能拿出能被复算的进度;出现次数回答的是什么时候该停下来换方法,同一个问题被反复记录就是明确信号;外部口径这一件在脚本之外,由验收人签字确认。

脚本的两个边界情况也试过:不给日志路径时直接打印用法并返回状态码 1;文件里没有一行符合格式时提示「没有读到有效记录」,同样返回 1,不会给出假的清零率。

六、一轮完整复盘长什么样

有了这张表和这个脚本,一周的节奏大概是这样。

周一到周五按自己的节奏练,每天收工前写一行日志。当天没有被问住的情况也要写一句「今天没有新增被问住的问题」,逼自己去主动制造一个,去题库里抽或者找人对练都行,空白的一天会让清单失真。

周末跑一次脚本,先看数量:新增几个问题,清零几个,清零率是不是比上一周高。这里要提醒自己一句,清零率上升不一定代表进步,也可能是这周练得太浅,压根没碰到难的问题,所以要和新问题数对着看。

再看清单里的老面孔。只要有一条挂着「出现 2 次」以上,下一周的头一件事就是处理它,排在学新东西前面。人很容易被揪出新问题的兴奋感带着走,这份清单的作用就是把顺序反过来,先把旧账还掉。

一圈走下来,你对进度的描述自然会变成能被复算的说法:上周被问住的四个问题,清零两个,还剩两个都没解决,其中一个已经先后撞上两次。

七、三种最常见的「假标准」

假标准的样子 为什么骗得过自己 换成什么
只记时长不记问题 时长越长越心安,问题数量始终没变也不会被发现 收工前必须写一条当天被问住的问题;确实没有就写「今天没被问住」,倒逼自己去制造一个
把收藏当完成 收藏夹里躺着几十篇,看起来像产出 每篇收藏必须对应表里的某一行,对应不上就删掉
面试只求次数不复盘 做够多少次这个数字很好看 每次结束一定留清单,下一场开场先验上一场的清单

这三种的共同问题是:它们都能让人在「我很努力」的感受里待很久,同时在被追问的那一刻一戳就散。假标准躲不过这套写法的原因很简单:它要求拿证据,而努力和感受给不出证据。

八、回到最初那句追问

按什么标准练的,问的是三件事:有没有外部口径,怎么判断该停下来,能不能给出能被复算的进度。前两件写进那张三列表,第三件交给上面的脚本。

写完之后再回答这句追问,答案就从模糊的时长变成了具体的清单:四个被问住的问题,清零两个,剩的两个一个还没动手,另一个第二次撞上还没解决。

同样是被问,这两个答案在面试官耳朵里的分量差得不止一点。

你上一次被问住的那个问题,现在清零了吗?

相关推荐
IT_陈寒1 小时前
Vite热更新失效?你可能也踩了这个坑
前端·人工智能·后端
桃西西呀1 小时前
LangGraph4j之一:客服请求分诊既要循环又要分流,我用 LangGraph4j 把控制流抽成了数据
人工智能·llm·ai编程
计算机编程指导师1 小时前
【计算机毕设选题推荐】基于Hadoop的宫颈癌变进程光谱数据分析系统源码 毕业设计 选题推荐 毕设选题 数据分析 机器学习
大数据·hadoop·python·数据分析·spark·毕业设计·宫颈癌变
geats人山人海1 小时前
java 4继承
java·开发语言
aqiu1111111 小时前
【C++算法打怪专栏】C++ `unordered_set` 常用初始化与插入方法总结
开发语言·c++·算法
leizhen198408091 小时前
中国 AI 反超的临界点,与世界格局正在发生的三重变化(漫画)
人工智能
行百里er1 小时前
Redis 模块——JSON、向量搜索与时序
redis·后端
Rosanci2 小时前
AI 写完不等于能用:以“验收标准 + 仓库检查”为中心的 AI 编程质控流程
人工智能·ai 编程
众链网络2 小时前
Agent 的成本大头不在“写“,在“判断“:拆解专用决策模型的三层架构
java·开发语言·人工智能·微服务