将比特列表分配到给定数量的槽中

Distribute list of bits into given amount of slots

给定如下位域(数字只能是 1 或 0):

const bits = [1, 1, 0, 1, 0, 0, 0, 1]

我想生成一个包含 N 个平均值的列表,其中 N 是任意数字。

在我们上面的示例中,给定 N 为 4,结果将是 [1, 0.5, 0, 0.5]。 (将数组2按2分组,然后计算每组的平均数)。

如果 N 为 2,则结果为 [0.75, 0.25]

到目前为止我一直在使用以下代码:

const average = (...args) => args.reduce((a, b) => a + b) / args.length;

const averageNumbers = Ramda.splitEvery(Math.floor(bits.length / N), bits).map(nums => average(nums))

问题是,如果我的 bits 数组由 696 个值组成,而我需要 150 个平均数,则上述方法不起作用,因为我最终有 174 个数字而不是 150 个。

我做错了什么?

如评论中所述,您最终得到 174 个数字而不是 150 个,因为 floor(696 / 150) 将位域分成 174 个 4 位块。

要获得平均值的近似值,您可以先将位域“扩展”到长度为 N 的倍数,然后再取平均值。

// Factor is the lowest number to expand bits by for its length to be a multiple of N
const factor = lcm(bits.length, N) / bits.length;

// Expand bits by the factor
const expandedBits = bits.map(bit => Array(factor).fill(bit)).flat(1);

const averages = splitEvery(Math.floor(expandedBits.length / N), expandedBits).map(nums => average(...nums));

// averages.length should now always be N