You need to enable JavaScript to run this app. 如何在Vega formula transform中使用阶乘实现二项分布PMF计算
优惠活动
大模型
产品
解决方案
定价
更多

如何在Vega formula transform中使用阶乘实现二项分布PMF计算

Vega JS 实现二项分布PMF直方图的解决方案

核心问题说明

Vega 表达式引擎为沙箱运行环境,仅支持官方定义的内置表达式,无法直接调用原生 JavaScript 的全局方法(如 Math.factorial),且默认未提供阶乘、组合数、二项分布相关计算函数。

实现思路

二项分布PMF公式为:$P(X=k) = C(n,k) \cdot p^k \cdot (1-p)^{n-k}$,其中 $C(n,k) = \frac{n!}{k! \cdot (n-k)!}$。
为避免大数值阶乘溢出、同时兼容Vega内置能力,提供两种可落地实现方案:


方案1:纯内置表达式实现(无需额外自定义代码)

通过对数转换规避阶乘溢出,完全使用Vega内置表达式完成计算:

  • 先声明二项分布参数:试验次数nval、单次成功概率pval
  • 生成所有可能的k值(取值范围0到n)
  • 分步计算对数累加项,最终转换为PMF概率值

对应配置片段

{
  "signals": [
    {"name": "nval", "value": 20},
    {"name": "pval", "value": 0.3}
  ],
  "data": [
    {
      "name": "dataset",
      "transform": [
        // 生成k值序列:0 到 nval(sequence的stop为*开区间*,因此取nval+1)
        {"type": "sequence", "start": 0, "stop": {"signal": "nval + 1"}, "step": 1, "as": "k"},
        // 生成1到k的序列,用于累加对数阶乘项
        {"type": "formula", "as": "log_factorial_k", 
         "expr": "sum(range(1, datum.k + 1), i => log(i))"},
        // 计算ln(n!) 和 ln((n-k)!)
        {"type": "formula", "as": "log_factorial_n", 
         "expr": "sum(range(1, nval + 1), i => log(i))"},
        {"type": "formula", "as": "log_factorial_nk", 
         "expr": "sum(range(1, nval - datum.k + 1), i => log(i))"},
        // 计算对数形式的PMF,再取指数得到最终概率
        {"type": "formula", "as": "pmf",
         "expr": "exp( log_factorial_n - log_factorial_k - log_factorial_nk + datum.k * log(pval) + (nval - datum.k) * log(1 - pval) )"}
      ]
    }
  ]
}

方案2:注册自定义表达式函数(适合复用场景)

如果需要频繁使用阶乘、二项分布计算,可通过Vega官方提供的自定义表达式注册能力,在初始化Vega实例前绑定JS方法,之后即可在表达式中直接调用:

  • 初始化Vega前注册自定义函数:
    // 注册阶乘函数
    vega.expressionFunction('factorial', function(n) {
      if (n < 0) return NaN;
      let res = 1;
      for (let i = 2; i <= n; i++) res *= i;
      return res;
    });
    // 注册直接计算二项分布PMF的函数
    vega.expressionFunction('binomialPMF', function(k, n, p) {
      if (k < 0 || k > n) return 0;
      const comb = factorial(n) / (factorial(k) * factorial(n - k));
      return comb * Math.pow(p, k) * Math.pow(1 - p, n - k);
    });
    
  • 配置中即可直接调用自定义函数计算y值,替换原错误的math.factorial逻辑:
    {"type": "formula", "as": "pmf", "expr": "binomialPMF(datum.k, nval, pval)"}
    

直方图绘制配置补充

计算完成PMF值后,直接绑定条形图标记即可完成绘制,核心映射规则:

  • X轴绑定k字段
  • Y轴绑定pmf字段
  • 条形宽度根据k值间隔设置,实现直方图效果

注意:Vega的sequence变换stop参数为开区间,生成连续整数序列时需将目标最大值加1作为stop值,避免最后一个k值缺失。


内容的提问来源于stack exchange,提问作者Jaidev V

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.11.03 09:36:00