1A2B猜数字游戏最优策略
把“猜数字”玩成算法题:这篇文章从零构建 1A2B 的最优求解思路,给出一个可靠基线(暴力一致性筛选),再用更聪明的“选猜”策略把平均轮数拉到约 4.3x。附交互示例、复现实验与参考资料。
游戏规则与术语
- 四位数,数字不重复,允许前导零(若不允许,可在实现中切换开关)。
- 判定规则:xAyB。A 表示数字与位置均正确的个数,B 表示数字对但位置不对的个数。
- 本文默认使用 Mastermind 风格的严格计分:如答案 5543,猜 5255 计 1A4B(允许重复输入时的定义)。若限制“输入也不重复”,则保持标准 1A2B 的去重计分。
目标与评价标准
- 目标:在“最坏情况轮数最小”的前提下,兼顾“平均轮数最小”。
- 已知下界与上界:
- 文献结论表明四位不重复数字的最坏情况上界为 7 轮;不存在 6 轮内保证解出的算法。
- 当前较优的平均轮数约为 4.34(不同实现/假设略有差异)。参考:Bullscows 综述。
基线方案 v1:一致性暴力筛选
- 思想:维护候选集合 candidates(所有可能答案)。任意给出一个猜测 guess,观察返回的 xAyB,将与该反馈“不一致”的候选全部剔除。下一轮在剩余候选里继续猜。
- 复杂度与表现:实现简单、鲁棒性高;平均轮数通常在 5.x 左右,是性价比极高的基线。
- 交互示例:
1 | 欢迎来到 1A2B 助手!每轮我会给出四位不重复数字,请输入反馈(如 2A1B 或 21)。 |
改进 v2:给“候选/询问”打分,优先问“信息量大”的问题
- 直觉:不是每个候选都同样好。当我们挑选下一次“要问的数字”时,应选择能把候选空间“切得更均匀”的那个,使得最坏分支尽可能小——这正是极大极小(minimax)的味道。
- 做法:
- 对每个可作为“询问”的四位数 q,枚举它对所有候选答案产生的反馈分布,将候选按反馈分桶。
- 记该分桶的“最大桶大小”为 score(q)。优先选择使 score(q) 最小的 q(最坏情况最小化)。
- 实践中常在“仅限候选内挑选”和“允许从全空间挑选”间权衡;后者可带来更整齐的分割,但计算更重。
- alpha-beta 是否有用:若将其抽象为博弈树,alpha-beta 提供的是对对抗搜索的剪枝框架;本问题评估函数昂贵、分支宽,但并非典型轮替对抗,因此更实用的是“分布统计 + 最坏桶最小化”的启发式。可把 alpha-beta 视作复杂情形下的工程优化而非必需品。
复杂度与问题性质
- 相关工作指出该类问题为 NP-hard,因而不存在已知的多项式时间最优算法;启发式带来的计算开销显著高于基线,但能换来平均轮数小幅提升。
- 参考:
实验与结果快照
- 基线(一致性筛选):平均约 5.5 轮左右(与你的生成策略、是否允许全空间提问有关)。
- 启发式(最坏桶最小化):可降至约 5.3/5.2,进一步结合更强的选猜与缓存,可靠近 4.3x 的前沿水平。
- 代价:每轮需要对大量“询问”做分布统计,时间与内存压力上升,工程上需做剪枝与缓存。
如何运行(复现)
- 仓库:见上方“代码仓库”。
- 关键开关:
- 是否允许前导零/是否允许输入重复数字
- 仅在候选集中选猜 vs. 从全空间选猜
- 评分策略:最坏桶最小化/期望桶大小最小化/混合策略
- 建议:先跑 v1 作为基线,再逐步开启评分与缓存,观测“平均轮数—耗时”的折中。
结论与要点
- 一致性暴搜是“既简单又强大”的基线;启发式的收益有限但稳定,适合对“步数更苛刻”的追求。
- 对于视频/文章演示,建议:
- 先用小样本可视化“候选集合如何被一次猜测切分”。
- 对比“随机选猜 vs. 评分选猜”的候选坍缩速度与最坏路径。
- 给出“我能否 6 步必解?”的悬念,再给出“理论上不可能”的答案,提升记忆点。
附:一次完整的人机交互样例
1 | [第0次] 请输入一个四位数字: 1234 |
参考与延伸阅读
Bullscows 最坏/平均轮数讨论与数据集整理:https://slovesnov.users.sourceforge.net/index.php?bullscows
HDU-1172 相关题目,可用于在线评测与算法练习
其他笔记/随感:
- 1, 九宫格(8数码), 16宫格(15数码)挪数字: 也是经典现实游戏: 吴昊品游戏
- 2, 自己果然没什么探究精神... "暴搜/16GB内存/4060ti/24小时期限"硬上, 完全不讲究优雅...