简介:这份资源是面向游戏行业求职者与数值策划入门者的笔试题库,聚焦数学、Excel与游戏设计三大模块,帮助读者系统检验并补强数值岗位的核心能力。压缩包内共1个docx文档,约29KB,内容以题目与参考答案对照的形式组织,便于自测与复盘。数学篇覆盖组合计数、多变量技能点分配、骰子概率、蒙提霍尔问题及兰切斯特方程坦克战损估算;Excel篇梳理SUM、COUNT、VLOOKUP、OFFSET、INDEX、RAND等函数用法与数组查询组合;游戏篇则围绕游戏币贬值治理、职业数值平衡、中毒效果叠加与属性衍生公式设计展开。目前已有970人学习下载,适合准备数值策划面试、希望用真题查漏补缺的读者,也可作为团队内部培训的参考素材。
1. 巨人数值策划笔试题到底在考什么:从一道“看起来像数学题”的伤害公式说起
如果你正在准备游戏数值策划的笔试,大概率会遇到一类题:给一张表、一段战斗日志、一个模糊的公式描述,让你反推伤害计算方式,或者让你在资源产出与消耗之间找平衡点。这类题在业内常被称作“巨人数值策划笔试题”,名字来源不重要,重要的是它背后考的东西非常具体——不是考你会不会背公式,而是考你能不能把一组混乱的数值关系拆成可验证的模型,再用最小改动让它跑通。
我见过不少新人在这类题上翻车,不是因为数学差,而是因为一上来就试图列一个“完美公式”,忽略了题目里给的边界条件。实际上,这类笔试的核心就三件事:识别变量、建立关系、验证边界。你不需要微积分,但需要清晰的逻辑和一点点“数值直觉”。下面我会按真实做题顺序,把这类题的拆解路径、常见参数设定、以及我踩过的坑一条条讲清楚。适合正在求职数值策划的人,也适合想转岗但没系统练过题的人。
2. 拆解题干:从“巨人数值策划笔试题”里提取可计算变量
2.1 先分清哪些是输入、哪些是输出、哪些是中间量
拿到一道数值题,第一件事不是算,而是画一张变量表。我一般会拿一张纸,左边写“题目直接给的数字”,右边写“题目问的结果”,中间留空。比如一道典型的伤害题会给你:攻击方攻击力、防御方防御力、技能倍率、暴击率、暴击伤害倍率、最终伤害值。那么输入就是前五个,输出是最终伤害,中间量可能是“减伤系数”“暴击期望”等。
这一步的关键是不要漏掉任何带单位的量。比如“攻击力”和“防御力”单位相同,但“技能倍率”是百分比,“暴击伤害倍率”也是百分比。单位不统一,后面列方程一定出错。我习惯把所有百分比转成小数,比如150%写成1.5,这样代入公式时不会多除一个100。
提示:如果题目里出现“等级”“品质”这类非数值变量,先假设它们只影响某个系数,不要急着给它们编公式。
2.2 用最小二乘法或试差法反推公式结构
很多巨人数值策划笔试题不会直接告诉你公式,而是给几组输入输出,让你猜公式。常见结构有乘法型、加法型、混合型。乘法型如:伤害 = 攻击 × 倍率 × (1 - 减伤),其中减伤 = 防御 / (防御 + K)。加法型如:伤害 = 基础伤害 + 攻击 × 系数。混合型最常见,也最容易被考。
我一般先用两组数据做比值,消掉未知常数。比如给两组攻击和对应伤害,假设公式是线性的,那么斜率就是系数。如果比值不是常数,就试除法。下面这段Python代码是我常用的试差脚本,用来快速验证假设的公式结构:
# 假设题目给了三组数据:攻击力atk,防御力df,最终伤害dmg # 先试一个常见公式:dmg = atk * skill_ratio * (1 - df / (df + K)) # 其中skill_ratio和K未知,用前两组数据解,第三组验证 import numpy as np data = [ (100, 50, 180), # atk, df, dmg (200, 50, 360), (100, 100, 120), ] # 从第一组和第二组看,df相同,atk翻倍,dmg翻倍 -> 线性于atk # 所以 skill_ratio * (1 - df/(df+K)) 对第一组是 180/100 = 1.8 # 对第三组,df=100,dmg/atk = 1.2 # 设 f(df) = 1 - df/(df+K),则 f(50)=1.8/skill_ratio, f(100)=1.2/skill_ratio # 两式相除消掉skill_ratio:f(50)/f(100) = 1.8/1.2 = 1.5 # 即 [1 - 50/(50+K)] / [1 - 100/(100+K)] = 1.5 # 化简: [K/(50+K)] / [K/(100+K)] = (100+K)/(50+K) = 1.5 # 解出 K = 50 K = 50 # 再代回第一组:skill_ratio * (1 - 50/100) = 1.8 -> skill_ratio * 0.5 = 1.8 -> skill_ratio = 3.6 skill_ratio = 3.6 # 验证第三组:100 * 3.6 * (1 - 100/150) = 360 * (1/3) = 120,正确 print("K =", K, "skill_ratio =", skill_ratio)这段代码的逻辑是:先通过比值消元,解出减伤公式里的常数K,再回代求技能倍率。参数说明:data里每行是攻击、防御、伤害;K是减伤常数,通常取50、100、200这类整数;skill_ratio是技能倍率,可能大于1。如果你试出来的K不是整数,或者验证第三组误差超过5%,说明公式结构不对,要换加法型或分段函数再试。
2.3 把“巨人数值策划笔试题”里的文字描述转成约束条件
有些题会写“防御越高,减伤效果越明显,但不会超过80%”。这就是一个约束:减伤上限0.8。还有“暴击率最高75%”“技能冷却不能低于1秒”。这些文字不是废话,是边界条件。我习惯在变量表旁边单独列一列“约束”,每写一个公式就检查是否满足。
比如你推出减伤 = 防御/(防御+100),那么当防御趋于无穷,减伤趋于1,但题目说上限80%,你就得改成减伤 = min(0.8, 防御/(防御+100))。或者用另一种形式:减伤 = 0.8 * 防御/(防御+100)。这两种处理方式在后续计算中结果不同,要看题目有没有给其他数据点来区分。
3. 建立数值模型:从单点计算到全局平衡
3.1 用表格法整理多组数据,避免手算混乱
一旦变量超过三个,手算就容易出错。我一般会拉一个表格,每行是一组输入,每列是中间量和输出。下面是一个典型的巨人数值策划笔试题数据表,我把它整理成Markdown表格,方便对照:
| 组号 | 攻击力 | 防御力 | 技能倍率 | 暴击率 | 暴击伤害 | 最终伤害 |
|---|---|---|---|---|---|---|
| 1 | 100 | 50 | 1.5 | 0.2 | 2.0 | 202.5 |
| 2 | 200 | 50 | 1.5 | 0.2 | 2.0 | 405.0 |
| 3 | 100 | 100 | 1.5 | 0.2 | 2.0 | 135.0 |
| 4 | 100 | 50 | 2.0 | 0.5 | 2.0 | 300.0 |
观察第1组和第4组:攻击、防御相同,技能倍率从1.5变2.0,暴击率从0.2变0.5,最终伤害从202.5变300。如果公式是“伤害 = 攻击 × 技能倍率 × 减伤 × (1 + 暴击率 × (暴击伤害 - 1))”,那么第1组:100×1.5×减伤×(1+0.2×1)=202.5,第4组:100×2.0×减伤×(1+0.5×1)=300。两式相除: (1.5×1.2)/(2.0×1.5)=1.8/3.0=0.6,而202.5/300=0.675,不相等。说明暴击部分不是简单乘(1+暴击率×(暴击伤害-1)),可能暴击伤害是独立乘区,或者暴击率有上限。
这种表格法能快速暴露假设错误。我一般会先算“无暴击”的伤害,再算“暴击期望”,对比题目给的最终伤害,看是否吻合。
3.2 用Python快速拟合参数,减少试错时间
如果题目给了五组以上数据,手算太慢,我会写一个小脚本做最小二乘拟合。下面这段代码假设公式为:伤害 = 攻击 × 技能倍率 × (1 - 防御/(防御+K)) × (1 + 暴击率 × (暴击伤害 - 1)),用scipy优化K和技能倍率:
import numpy as np from scipy.optimize import minimize # 输入数据:atk, df, skill, crit_rate, crit_dmg, actual_dmg data = np.array([ [100, 50, 1.5, 0.2, 2.0, 202.5], [200, 50, 1.5, 0.2, 2.0, 405.0], [100, 100, 1.5, 0.2, 2.0, 135.0], [100, 50, 2.0, 0.5, 2.0, 300.0], ]) def model(params, atk, df, skill, crit_rate, crit_dmg): K, base_ratio = params reduction = 1 - df / (df + K) crit_expect = 1 + crit_rate * (crit_dmg - 1) return atk * skill * base_ratio * reduction * crit_expect def loss(params): pred = model(params, data[:,0], data[:,1], data[:,2], data[:,3], data[:,4]) return np.sum((pred - data[:,5])**2) res = minimize(loss, [100, 1.0], bounds=[(1, 1000), (0.1, 10)]) print("K =", res.x[0], "base_ratio =", res.x[1], "loss =", res.fun)这段代码的逻辑是:定义模型函数,用最小二乘拟合两个未知参数K和base_ratio。参数说明:K是减伤常数,初始猜100;base_ratio是基础倍率,初始猜1.0;bounds限制范围避免负数。如果拟合后的loss大于1,说明公式结构不对,需要换模型。我一般会试三四种结构,取loss最小的。
注意:拟合出来的参数不一定唯一,可能多组参数都能拟合数据。这时候要看题目有没有额外约束,比如“K取整数”“技能倍率不超过3”。
3.3 从单点公式扩展到资源产出与消耗平衡
巨人数值策划笔试题不只有战斗公式,还有经济系统题。比如“玩家每天获得1000金币,升级一件装备需要500金币,升10级后每级递增20%,问多少天能升满”。这类题的核心是识别增长模型:线性、指数、还是分段。
我一般先写递推式:第n级费用 = 500 × (1.2)^(n-1),总费用 = 500 × (1.2^10 - 1)/(1.2 - 1)。然后算每天净收入,再算天数。如果题目还给了“玩家有初始金币”,就加进去。下面是一个通用计算脚本:
# 计算升满N级所需总费用和天数 base_cost = 500 growth = 1.2 levels = 10 daily_income = 1000 initial_gold = 0 total_cost = sum(base_cost * (growth ** i) for i in range(levels)) days = (total_cost - initial_gold) / daily_income print(f"总费用: {total_cost:.2f}, 需要天数: {days:.2f}")参数说明:base_cost是第一级费用,growth是每级增长率,levels是总级数,daily_income是每天净收入。如果days不是整数,通常向上取整。如果题目要求“不能有小数天”,就取ceil。
4. 避坑指南:巨人数值策划笔试题里最容易翻车的五个点
4.1 现象:公式拟合完美,但代入边界值就崩
原因:只用了中间数据拟合,没检查边界。比如减伤公式在防御=0时应该减伤=0,在防御极大时趋近上限。如果拟合出的K是负数,防御=0时减伤会变成负数,直接翻车。
解决:拟合后必须代入防御=0、防御=10000、攻击=0、暴击率=0、暴击率=1这几个边界,看结果是否合理。不合理就换公式结构。
4.2 现象:暴击期望算错,把暴击伤害当成独立乘区
原因:暴击伤害倍率通常是在暴击时替换普通伤害,而不是额外乘。比如普通伤害100,暴击伤害倍率2.0,暴击时打200,期望是100×(1-暴击率)+200×暴击率=100×(1+暴击率)。如果写成100×(1+暴击率×2.0),就多算了。
解决:先明确暴击伤害的定义。如果题目写“暴击造成200%伤害”,那就是替换;如果写“暴击额外造成100%伤害”,那就是加法。我一般会看题目给的最终伤害值,反推是哪种。
4.3 现象:资源产出题里忘记初始值或一次性奖励
原因:题目说“玩家初始有500金币,每天获得1000,第3天额外获得2000”,你只算了每天1000,漏了初始和额外。
解决:把时间轴画出来,每天的收入列清楚,初始值单独加。我习惯用表格:第0天初始,第1天收入,第2天收入……额外奖励标红。
4.4 现象:百分比和绝对值混用,导致量纲错误
原因:比如“攻击力提升10%”和“攻击力提升10点”,前者是乘法,后者是加法。如果题目同时给,要先算乘法再算加法,还是反过来?通常游戏里是先加固定值再乘百分比,但要看题目描述。
解决:统一转成小数,固定值单独列。我一般写:最终攻击 = (基础攻击 + 固定加成) × (1 + 百分比加成)。如果题目没明确,就试两种顺序,看哪个符合给出的数据。
4.5 现象:忽略取整规则,导致最后一位数对不上
原因:游戏数值经常取整,比如向下取整、四舍五入。题目给的最终伤害可能是取整后的,你算出来是202.5,题目写202,就差0.5。
解决:在公式最后加int()或round(),试哪种取整方式能让所有数据匹配。我一般先试向下取整,再试四舍五入。
5. 进阶技巧:用“反向出题”验证你的数值模型
5.1 自己改一个参数,看输出是否合理
做完一道巨人数值策划笔试题后,我习惯把攻击力翻倍,看伤害是否翻倍;把防御力翻倍,看减伤是否增加但不超过上限;把暴击率从0调到1,看伤害是否线性增长。如果某个参数变化导致输出突变(比如防御从99到100,伤害从200掉到50),说明公式有分段或阈值,题目可能故意考这个。
下面这段代码可以快速做敏感性测试:
def damage(atk, df, skill=1.5, crit_rate=0.2, crit_dmg=2.0, K=100): reduction = 1 - df / (df + K) crit_expect = 1 + crit_rate * (crit_dmg - 1) return atk * skill * reduction * crit_expect # 测试防御从0到200,步长20 for df in range(0, 201, 20): print(f"df={df}, dmg={damage(100, df):.2f}")如果输出是平滑下降,说明公式连续;如果有跳变,说明有分段。我一般会画个简单的折线图(用matplotlib),肉眼一看就知道。
5.2 用“极端值”检查公式是否满足题目隐含约束
题目可能写“防御收益递减”,那么防御从0到100的减伤增量应该大于从100到200的增量。你可以算二阶差分,如果二阶差分小于0,就是递减。如果题目写“暴击率最高75%”,你就把暴击率设成0.75和0.76,看伤害是否不再增长。
我一般会列一个检查表:
| 检查项 | 操作 | 预期 |
|---|---|---|
| 减伤上限 | 防御=10000 | 减伤≤0.8 |
| 暴击上限 | 暴击率=1.0 | 伤害=攻击×技能×减伤×暴击伤害 |
| 攻击为0 | 攻击=0 | 伤害=0 |
| 技能倍率为0 | 技能=0 | 伤害=0 |
如果任何一项不满足,就回去改公式。
5.3 把答案写成可复现的步骤,而不是只给最终数字
笔试时,阅卷人看的不仅是结果,还有你的推导过程。我习惯把每一步写清楚:先列变量,再写假设,再代入数据,再验证。即使最后数字算错,过程对也能拿大部分分。下面是我常用的答题模板:
- 定义变量:攻击A,防御D,技能倍率S,暴击率C,暴击伤害M,减伤常数K。
- 假设公式:伤害 = A × S × (1 - D/(D+K)) × (1 + C×(M-1))。
- 代入第一组数据,解出K和S。
- 用第二组数据验证,误差小于5%。
- 写出最终公式,并注明约束:减伤上限0.8,暴击率上限0.75。
这套流程我用了很多次,基本能覆盖大部分巨人数值策划笔试题。最后说一个我自己的教训:有一次我为了追求公式“优雅”,把减伤写成了指数形式,结果拟合出来的参数虽然好看,但代入边界直接爆炸。后来我学乖了,优先用线性或分式,除非题目明确要求指数。数值策划的笔试,稳比炫重要。希望帮到你。
本文还有配套的精品资源,点击获取