You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

将模乘逆元函数转换为数组公式的问题求助

解决方案:实现数组化的模乘逆元计算

针对你需要批量计算模乘逆元、适配不定长度密钥数组的需求,提供两种可行方案:

方案一:使用原生Google Sheets公式(无需自定义函数)

利用BYROW函数遍历密钥列的每个元素,对单个元素应用你原有的逆元计算逻辑,自动适配数组长度:

=BYROW(L:L, LAMBDA(x, IF(x="", "", IF(ABS(E2)=1, 0, SIGN(E2)*MATCH(1, INDEX(MOD(ROW(INDIRECT("1:"&ABS(E2)))*SIGN(E2)*x, ABS(E2)), 0), 0)))))

说明:

  • BYROW(L:L, LAMBDA(x, ...)):遍历L列的每个单元格x,对每个x执行后续计算
  • IF(x="", "", ...):跳过空单元格,避免无效计算
  • 核心逻辑沿用你原有的逆元判断逻辑,确保和单个单元格计算结果一致

方案二:自定义高效数组逆元函数(推荐大模数/大量密钥场景)

原生公式通过遍历找逆元的效率较低,针对大模数或大量密钥的情况,用扩展欧几里得算法实现自定义函数,直接处理数组输入:

  1. 在Google Sheets中打开「扩展程序」→「Apps脚本」,替换原有代码为:
function MOD_INVERSE_ARRAY(modulus, keys) {
  // 处理模数输入(支持单个单元格或数组)
  const mod = typeof modulus === 'object' ? modulus[0][0] : modulus;
  const positiveMod = Math.abs(mod);
  const sign = Math.sign(mod);

  // 扩展欧几里得算法:计算单个a在模m下的逆元
  function modInverse(a, m) {
    let m0 = m;
    let y = 0, x = 1;
    if (m === 1) return 0;

    while (a > 1) {
      const q = Math.floor(a / m);
      [m, a] = [a % m, m];
      [y, x] = [x - q * y, y];
    }

    return x < 0 ? x + m0 : x;
  }

  // 处理密钥输入(支持单个值或数组)
  if (typeof keys === 'string') {
    const key = parseInt(keys);
    return isNaN(key) ? ["无效密钥"] : [[sign * modInverse(key, positiveMod)]];
  } else {
    return keys.map(row => {
      const key = parseInt(row[0]);
      if (isNaN(key) || row[0] === "") return [""];
      try {
        return [sign * modInverse(key, positiveMod)];
      } catch (e) {
        return ["无逆元"];
      }
    });
  }
}
  1. 在工作表中使用函数:
=MOD_INVERSE_ARRAY(E2, L:L)

说明:

  • 自动适配L列的所有非空密钥,空单元格返回空
  • 若密钥和模数不互质(无逆元),返回「无逆元」提示
  • 扩展欧几里得算法比遍历法效率高10倍以上,适合大模数场景

为什么你之前的尝试失败?

  • 直接用L:L作为原公式输入:原公式未做数组化处理,MATCH无法处理多值数组,导致报错
  • SPLIT方法:SPLIT用于拆分文本字符串,无法实现数组遍历,只会将单元格内容拼接后计算,导致结果错误

内容的提问来源于stack exchange,提问作者Collin Dehmer

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.19 23:55:31