科举乡试答题结束后,结果页中央人物并不是可靠的长期识别依据。真实开发中,旧模板依赖考官形象,当结果页更换人物后,页面已经完成但模板分数明显下降,流程就可能继续把结果页当成答题页。当前金手指把完成态改为识别固定结果文字,并在每次准备点击答案前检查结果页,让“是否完成”先于“点击哪个答案”。
为什么人物大图容易成为脆弱模板
人物图像面积大、视觉特征丰富,看起来很适合模板匹配,但它包含了与业务状态无关的变化:角色立绘可能替换,背景特效可能改变,窗口缩放也会影响边缘和纹理。模板即使在旧页面上得分很高,也不能证明新结果页仍然使用同一人物。完成判断真正关心的是页面语义,而不是画面中出现哪位考官。
开发修正时,结果页被拆成两类稳定信息。中央结果文字覆盖正确率不同的页面,包括“恭喜少侠”和低分提示共同的固定前缀;底部绿色复活令说明在两类结果页都存在,可作为独立佐证。任一稳定文字达到配置阈值即可确认完成,不再要求人物与文字同时出现。

限定搜索区域比全屏查字更重要
相同汉字可能出现在聊天、任务栏、活动列表或其他弹窗。当前配置分别限定中央结果文字区域与底部说明区域,只在窗口相对范围内做匹配。窗口移动后,区域跟随客户区重新计算;窗口缩放时,模板使用有限的多尺度搜索。限定区域减少无关候选,也让日志中的最高分更容易解释。
文字模板采用灰度匹配,是为了降低轻微颜色和亮度变化带来的干扰,但灰度不等于忽略布局。模板仍保留字形、间距与局部背景结构,且必须落在预期结果区域。中央结果文字阈值和底部说明阈值分别配置,因为两块区域的字号、颜色与抗锯齿条件不同。
多个模板必须独立计算自己的分数
一次开发复现还暴露了缓存边界问题:连续检查两张临时灰度模板时,如果诊断缓存只依赖对象标识,Python 复用已经释放的临时对象标识,就可能让第二张模板错误沿用第一张分数。修正后的完成检查让每张结果模板独立执行完整多尺度搜索,直接读取自己的最佳分数。
这条经验适用于更广泛的 Windows 图像识别:缓存键必须代表真实图像内容、模板路径和搜索条件,不能只依赖生命周期短的内存对象;诊断用的加速也不应改变业务结果。出现“两张模板单独测都正常,连续测第二张异常”时,应优先检查缓存归属,而不是盲目降低阈值。
为什么每次点击答案前都检查完成态
科举最后一题提交后,结果页可能立即出现。如果只按固定点击次数检查一次,页面切换的时间差可能让流程在结果页再点答案区域。当前科举配置把完成检查频率设为每题一次:准备点击任一答案前,先截取当前窗口,检查中央结果文字和底部说明;确认完成后立即结束本窗口答题,不再发出答案点击。
检查顺序也很关键。先识别答题面板、再点击、最后判断完成,会把最危险的动作放在验证之前;先判断完成,再确认仍在答题页,最后点击候选,才能让结果页成为停止条件。这个模式同样适合“按钮消失即完成”不够稳定的其他流程。
排错时应保存哪些证据
若结果页仍被漏判,保留一张隐藏账号、消息和用户名后的完整窗口截图,同时记录窗口尺寸、系统 DPI、中央模板分数、底部模板分数以及本次检查使用的区域。不要只裁一小块文字,因为需要验证相对区域是否算对、页面是否被弹窗覆盖、缩放后模板是否落在搜索范围。
这次修正不依赖虚构的用户效果或收录数据,依据来自当前答题配置与开发记录。想了解多尺度搜索的基础,可阅读OpenCV 多尺度模板匹配实践;其他真实技术记录可从开发日志与使用技巧继续查看。

