class PachinkoTree {
constructor(array) {
const buffer = [-Infinity];
const depth = Math.ceil(Math.log2(array.length));
const length = 2 ** (depth + 1);
for (let i = 0; i < length / 2; i++) buffer[i] = 0;
for (let i = length / 2; i < length; i++) buffer[i] = -Infinity;
const { random } = Math;
for (const v of array) {
let k = 1;
for (let i = 0; i < depth; i++) {
++buffer[k];
const l = buffer[k + k];
const r = buffer[k + k + 1];
k += k;
if (l > r) k++;
else if (l === r) k += (random() * 2) | 0;
}
buffer[k] = v;
}
this.buffer = buffer;
this.depth = depth;
}
toIndices() {
const output = [];
const { buffer } = this;
for (let i = buffer.length / 2; i < buffer.length; i++) {
if (Number.isFinite(buffer[i])) output.push(buffer[i]);
}
return output;
}
}