Roguelite 里最迷人的句子往往是「这局完全不一样」。最烦人的句子则是「这局纯粹搞我」。两者都可能来自同一套 RNG,差别通常不在随机函数本身,而在随机被放在系统的哪一层、有没有给玩家可学习的规律。
我后来把随机问题拆成三件事:池子是否干净、权重是否可解释、失败是否公平可追溯。做不到第三点,玩家会把「方差」听成「恶意」。

1. 表驱动:让策划能「看见」分布
与其在代码里散落 if (rand() < 0.3),我更愿意把掉落、商店、事件门收进表:
- 条目 id、基础权重、解锁条件、互斥标签;
- 最小间隔(同一负面事件多久内不重复);
- 保底与封顶(硬上限防脸黑,软下限防无聊)。
表的价值不是「方便改数」,而是分布可被讨论。团队能指着一行说:这条在第三层出现是否太早。
2. 池化:全池随机常常是设计偷懒
「从所有道具里抽」听起来公平,实际上会破坏构筑学习曲线:玩家学不到「这一局在鼓励什么玩法」。我倾向:
- 分层池:早期池、中期池、Boss 前池;
- 构筑池:与当前已持有道具标签相关的子池加权;
- 污染控制:强力组合的出现需要前置条件,而不是纯运气叠乘。
随机在这里服务的是叙事节奏,不是彩票机。
3. 可学习性:玩家需要「翻车理由」
真正的挫败来自不可归因:不知道为什么死、不知道为什么穷、不知道为什么永远缺那一块拼图。我会检查:
- 危险是否有可读预警(动画、音效、UI);
- 资源曲线是否在若干局内可对比(同一策略为何有时暴毙);
- 是否有「教科书局」让核心机制被自然复习。
随机可以残酷,但要残酷得可复盘。否则社区只会留下一句「运气游戏」。
4. 真随机 vs 可控方差:我如何选
- 真随机适合:装饰性掉落、次要奖励、无关紧要的事件调味。
- 可控方差适合:核心资源、决定构筑方向的升级、可能导致软锁的钥匙道具。
可控不等于固定,而是把方差关进规则:例如「三局内必出现一次恢复手段」这类不破坏惊喜、但防止连续绝育的设计。
5. 加权抽样的实现:别在热路径里做「重复扫描」
表驱动之后,运行时要把权重变成一次抽取。朴素做法是:
roll = random_uniform(0, sum(weights))
acc = 0
for each item:
acc += item.weight
if roll < acc: pick item
条目少时完全够用。条目多、每帧多次抽取时,我会考虑:
- 前缀和 + 二分:预处理
cumsum,每次O(log n); - Alias Method:预处理
O(n),每次抽取O(1)(实现略繁,但商店刷新、批掉落很香)。
实现细节里还有两个坑:
- 浮点累加误差:用整数权重(例如放大 1000 倍)有时更稳;
- 动态权重:解锁、标签过滤后池子变化,要定义缓存失效时机,避免拿着过期前缀和抽。
6. 保底、怜悯与「伪独立」:玩家感受到的是序列,不是分布
数学上每次独立抽取可以符合「1% 传说」;体验上玩家记住的是连续三十次没出。所以我会显式维护序列层规则:
- 硬保底:第 N 次必出(或必出池内子集之一);
- 软保底:未命中则下次权重乘倍数,命中后重置;
- 负相关:同一 run 内某些强力事件互斥或强冷却,避免「一局把彩票兑完」。
这些都会改变边缘分布,不再是独立同分布。调试时要在工具里同时显示「单抽概率」与「整局期望」,否则策划和程序会对同一个数吵一晚上。
7. RNG 种子:要可复现,也要防作弊
单机游戏常纠结存档与读档。完全固定种子利于复现 bug(同一 seed 重放同一地图与掉落),但也会让 S/L(存档/读档)变成可控刷首抽。
我的折中通常是:
- 世界生成与战斗外事件用一层种子;
- 战斗内暴击/掉落可与 run 内递增计数器混合,降低 S/L 粒度;
- 开发构建强制记录
seed + decision log,发布构建再关。
联机或排行榜若涉及随机,要另写威胁模型,这里不展开。
8. 共现与「组合爆炸」:矩阵比柱状图更有用
除了单道具出现率,我会算二元共现:(P(A \cap B)) 与 (P(A)P(B)) 的比值偏离,往往暴露:
- 同一池子里标签未互斥;
- 权重函数不小心对某标签二次计数;
- 关卡掉落表与全局表叠乘。
三元以上组合爆炸时,用频繁模式挖掘或只看「Top 构建标签集合」也能抓大头。
9. 与难度曲线的耦合:随机是调音台,不是噪音发生器
同一套道具池,在「第三层」与「Boss 前一层」应有不同有效强度。我会给层数乘子或给池子分段,而不是全局一张表抽到通关。
Boss 战前若需要「补资源」,与其偷偷调爆率,不如显式插入恢复事件节点——玩家能学会「节奏上有喘息」,比暗改 RNG 更不容易被骂「暗箱」。
10. 「教科书局」与信息经济学
Roguelite 的学习依赖可重复的实验。若核心机制藏在极低概率事件后面,玩家学不到因果。我会预留:
- 教学层或首 run 的窄池;
- 或「第一次必见」的伪随机(仅一次),之后回归全局表。
这不是降低深度,是把深度从蒙眼试错迁到可读博弈。
11. 遥测:随机也要被度量
上线后我会看:
- 道具出现频率与共现矩阵;
- 关卡放弃点是否与特定事件簇相关;
- 速通与休闲玩家的分布尾部差异;
- 保底触发率:若长期逼近 100%,说明主表设计过苛。
没有数据,调权重只能靠直播间弹幕。
12. 收束
Roguelite 的随机是作曲,不是掷骰子。表驱动让分布可见,池化让节奏可控,可学习性让玩家愿意再来一局;实现上把加权抽样、序列规则、种子与遥测当作一等公民,才不会在「明明数学没问题」的地方输掉口碑。翻车若可复盘,玩家会骂 RNG;翻车若不可复盘,玩家会骂设计——后者难洗得多。