
从一节 Vue3 直播课到“边玩边学”:我把扫雷做成了会算概率的教练
肉山扫雷最早是我 Vue3 讲习班的教学项目,现在它会给每一格算踩雷概率、给每一步打分,还能逐步回放复盘。
这个扫雷最早是我做的一个免费线上讲习班“使用 Vue3 开发扫雷游戏”的教学项目。课程视频发在 B 站上,从用 display:grid 画地图、生成地雷开始讲起。课讲完之后,代码就一直放在 minesweeper.meathill.com 上。
很多人玩扫雷只会“凭感觉点”,输了也不知道自己是运气差还是判断错了。所以我把它改成了“肉山扫雷——边玩边学”,现在的版本是 v0.10。
边玩边学:把概率算出来,给每一步打分
在学习模式里,最核心的是概率热力图。每一个还没翻开的格子,系统都会算出它是雷的概率,并用绿-黄-红的颜色叠在格子上,也可以直接切换成百分比显示。
除了告诉你概率,系统还会给你的每一步操作打分。评分依据是你点击那一格与当时最优选择之间的概率差,差距满 0.5 就会扣到 0 分。这样一来,一局顺风的盘面不会被系统性打低分。除了翻开格子,拔旗操作也会被单独评分。
复盘图表记录了你每次操作的速度和决策质量,并用曲线标出高风险的盲猜操作。每一步都存了完整的棋盘快照,点击图表上任意一点,棋盘就能恢复到那一步刚下完的样子。你还可以通过时间滑块缩放到具体的某一段,甚至能把整局数据导出为 JSON 文件。另外,我还做了一个独立的概率计算器页面,方便你把在别处遇到的盘面摆出来计算。
算法里的两个坑和一个取舍
在做概率计算时,我踩过两个坑,也做了一次关键的取舍。
第一个坑是插旗。一开始,概率计算会“相信”玩家插的旗。但旗子只是玩家自己的标记,很有可能插错。插错的旗会让周围本来危险的格子被误判成安全。后来我把逻辑改成只根据已经翻开的数字进行计算。旗格本身也会显示概率,你可以对照着看“我以为这里是雷,求解器到底有多大把握”。
第二个坑来自近似算法。有用户截图反馈,一个“1”旁边明明必然是雷的格子,居然被算成了 47%。原因是在未翻开格子太多时,我直接取了平均近似。修法是先把必雷和必安全的格子找出来,剩下的格子再去做近似。
修完之后,在困难难度中盘又遇到了卡死,一次计算要花 13.5 秒。为了兼顾性能,我加上了搜索预算,把实时计算时间降到约 0.1 秒。剩下的精算工作放到浏览器空闲时在后台慢慢算,算出来之后再合并进热力图。我的原则是:宁可标“近似”,也不能误判。
藏在手感里的小细节
除了算法,我也花了不少心思调手感。首次点击必定是空白格,也就是周围 3×3 区域不放雷;右键在“无 → 旗 → 问号”之间循环;右键拔旗后 200 毫秒内会忽略同一格的左键点击,防止误触爆雷;针对 Mac 的妙控鼠标和触摸板,支持用双击代替左右键同按;快捷键支持 F2 或 N 新开一局、H 提示、L 开关学习模式;手机端则禁止了双击缩放。
游戏目前支持 6 种语言,右上角有评论按钮,可以直接给我留言。
如果你想知道自己到底是“运气差”还是“算错了”,可以来 minesweeper.meathill.com 打一局,然后看看复盘。