☰
Seed-2.1-pro 择校平台:官网表格清洗、简章截图识别到产品上线全链路
2026/9/26 4:43:16 网站建设 项目流程

考研择校最耗时间的环节,往往不是做决策,而是把散落在官网表格、PDF 与简章截图里的信息凑成一张可横向比较的表。一所院校一份招生目录,十所院校就是十种表头结构。

常规做法在这里明显不够用:写死选择器的爬虫经不起年年改版,OCR 只能出纯文本还得二次解析,人工复制粘贴又慢又容易抄错年份。确定性的代码搞不定版式多变的图片,纯靠模型又守不住字段精度。

本文分享一套可直接跑通的落地方案:pandas 表格清洗 + Seed-2.1-pro 多模态读图 + FastAPI 检索接口与筛选前端,可直接落地。

一、痛点:择校数据散落在表格与截图里

把考生卡住的地方先摆出来,一共是三处信息断层:

  • 官网表格零散:招生目录与复试线以 Excel、PDF 分发,字段名和表头位置每年都在变。
  • 关键数据是图片:报录比、复试名单常以截图形式贴在通知里,无法直接检索和比对。
  • 人工比对成本高:横向对比十几所院校,光是复制粘贴就要耗掉大半个下午。

核心结论:择校平台的第一性问题不是推荐算法,而是把异构信息收敛成可比的结构化字段。

二、链路:官网数据到可查服务的四段流水

整条链路拆成四段流水,每一段只负责一件事,先看全局:

官网表格 → pandas 清洗 → Seed-2.1-pro 读图 → 字段合并校验 → 检索接口 → 筛选前端

  • 采集段:只负责拿到原始 Excel 与截图,不做任何业务判断,方便替换来源。
  • 抽取段:表格走确定性代码,图片走多模态模型,两条通道并行互不阻塞。
  • 服务段:合并后的记录落进 SQLite,由 FastAPI 统一暴露查询接口。
  • 呈现段:静态页面只调接口,完全不接触模型与清洗逻辑,前端可独立迭代。

核心结论:把不确定性最大的读图环节单独隔离,其余三段都能用普通工程手段写单测。

三、表格抽取:官网 Excel 清洗成结构化记录

官网 Excel 的表头位置年年变,先做结构探测再取数:

  • 表头探测:用关键字匹配定位真实表头行,避免把行号写死在代码里。
  • 类型收敛:招生人数转数值型,非数字行在读入阶段直接丢弃。

下面这段代码用 pandas 定位含“专业代码”的表头,向下取数并统一列名,适配常见招生目录表:

importpandasaspddefload_major_table(path):df=pd.read_excel(path,header=None)mask=df.astype(str).apply(lambdar:r.str.contains('专业代码').any(),axis=1)hdr=int(mask.idxmax())# 定位真实表头行body=df.iloc[hdr+1:].reset_index(drop=True)body.columns=['major_code','major_name','plan','subject','line']body=body.dropna(subset=['major_code'])body['plan']=pd.to_numeric(body['plan'],errors='coerce')returnbody.dropna(subset=['plan'])

先探测表头、再取数、最后做类型转换,脏行在读入阶段就被剔除。

核心结论:表格通道追求 100% 确定性,任何一行进不了 schema 就地报错,不带病入库。

四、截图识别:多模态模型读出招生字段

简章截图交给 Seed-2.1-pro,让它按固定模板吐字段:

  • 提示词锁格式:明确列出字段名并要求缺失填 null,禁止输出解释性文字。
  • 温度压到 0.1:抽取任务不需要创造性,低温度能显著降低字段漂移。
  • 单图单请求:一张截图对应一次调用,失败可单独重试且不污染其他记录。

下面这段代码完成图片 base64 编码、提示词组装与返回解析,可直接对接 Seed-2.1-pro 的 OpenAI 兼容端点:

importbase64,json,requestsdefread_admission_shot(img_path,api_key):b64=base64.b64encode(open(img_path,'rb').read()).decode()content=[{'type':'image_url','image_url':{'url':'data:image/png;base64,'+b64}},{'type':'text','text':'提取院校名称、专业代码、复试分数线、招生人数,''只输出 JSON,缺失字段填 null'}]payload={'model':'seed-2.1-pro','messages':[{'role':'user','content':content}],'temperature':0.1}r=requests.post('https://ark.example.com/api/v3/chat/completions',headers={'Authorization':'Bearer '+api_key},json=payload,timeout=60)returnjson.loads(r.json()['choices'][0]['message']['content'])

低温度 + JSON 约束 + 单图单请求 = 可直接入库的字典。

五、字段对齐:合并表格行与图片抽取结果

两条来源拿到同名字段时,必须有一套可执行的合并顺序:

表格主键定位 → 图片补空缺 → 冲突打标 → 人工复核队列

字段表格来源图片来源合并策略
院校名称表内抬头简章页眉一律以表格为准
复试分数线分数列模型识别值不一致则标need_review
招生人数计划列简章正文表格缺失时才用图片补齐
专业代码首列章节标题长度不足 4 位直接判失败
  • 主键优先:院校代码加专业代码构成主键,图片内容只作为属性补充。
  • 冲突不覆盖:两侧数值不一致时不自动取舍,标记留给人工复核流程。

核心结论:合并规则写死在代码里,比让模型临场判断更可控、更可回溯。

六、规则校验:给分数与招生人数加一道闸门

模型会幻觉,规则层必须在入库前拦下脏数据:

下面这段校验函数在记录入库前统一执行,返回状态与错误原因,可挂到任意批处理管道:

defvalidate(rec,year=2025):errs=[]line=rec.get('line')or0ifnot(150<=line<=400):errs.append('分数线超出合理区间')if(rec.get('plan')or0)>1000:errs.append('招生人数异常')ifrec.get('year')!=year:errs.append('数据年份不符')rec['status']='pass'ifnoterrselse'review'rec['errors']=errsreturnrec
  • 区间校验:复试线落在 150~400 之外,基本可判定为识别或抄录错误。
  • 状态分流:通过的记为pass,异常的记为review并附具体错误原因。

规则层兜底,模型输出永远不直接进库。

七、检索接口:按分数地区专业返回候选院校

检索接口只认结构化字段,四个参数决定一次查询:

参数类型示例作用
scoreint365按线差排序的考生初试分
regionstr华东限定院校所在大区
majorstr0854专业代码前缀匹配
limitint10返回条数,默认 10
  • 线差排序:用考生分数减院校复试线,按差值从高到低排,天然分出保底与冲刺。
  • 前缀匹配:专业代码支持前缀检索,0854可一次召回整个计算机专硕大类。

核心结论:接口参数越少越稳定,复杂度留在排序策略里而不是暴露给调用方。

八、前端筛选:让考生三步找到目标院校

页面设计成三步筛选,考生完全不需要理解数据结构:

  • 第一步填分数:输入初试总分,即时显示可冲击院校数量,给出正反馈。
  • 第二步选范围:地区与专业代码用下拉多选,避免自由输入带来的空结果。
  • 第三步看卡片:每张卡片展示复试线、招生人数、线差与数据来源年份。

交互只暴露结果,字段复杂度全部留在后端。

九、部署启动:一键拉起接口与静态页面

部署拆成后端接口与静态页面两条进程,各自独立做健康检查:

下面这段脚本在一台干净的 Linux 机器上完成依赖安装、接口启动、静态资源托管与连通性验证:

pipinstall-rrequirements.txtexportSEED_API_KEY=xxxx uvicorn server:app--host0.0.0.0--port8000&python-mhttp.server5173--directorywebcurl-shttp://127.0.0.1:8000/health
  • 密钥外置:API Key 只走环境变量,禁止写进仓库或前端 JS。
  • 健康探针:/health返回 200 才放行前端,避免白屏后无从排查。

接口与页面分离启动,健康检查通过即视为服务可访问。

十、排错验收:常见故障与定位路径

上线后的问题集中在四类,按现象到路径逐一排查:

现象可能原因定位动作
表格读入为空表头行判断错位打印df.head(15)核对关键字
读图接口超时单图体积过大压到 1MB 以内再重试
分数线全为 null提示词未锁 JSON检查返回是否被包成自然语言
检索返回空专业代码写成中文名改用代码前缀替代名称查询
  • 复现优先:先用一条真实记录跑通全流程,再改代码,避免在猜测中调试。
  • 留痕入库:每次抽取都保存原始图片路径与模型原始返回,便于事后回溯。

核心结论:排错表直接贴进仓库 README,比口头经验更耐用。

结语

这条链路的价值在于分工清晰:pandas 负责确定性的表格,Seed-2.1-pro 负责版式多变的图片,规则层负责最后一道闸门,三者各司其职,任何一环失效都能被定位到具体日志。换一个年份的招生数据,只需替换输入文件,清洗与校验代码基本不动。

产品化之后,它不再是一个数据脚本,而是能被前端调用、能被运维监控、能被考生直接使用的可运行服务,后续接上收藏、对比与志愿表生成也有清晰的挂载点。

数据来源再乱,只要经过“抽取—校验—合并”三道工序,都能变成可检索的择校决策依据。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询