通过均匀分布值有效地合并两个数组

Efficiently merge two arrays by distribute values evenly

我见过很多 question/answer 通过交替值合并两个数组。他们是这样工作的:

let array1 = ["a", "b", "c", "d"];
let array2 = [1, 2];

let outcome = ["a",1 ,"b", 2, "c", "d"] 

但我希望根据数组大小均匀分配值,从而提高输出效率。

expected outcome = ["a","b", 1, "c", "d", 2] 

其他场景

let array2 = [1];
expected outcome = ["a","b", 1, "c", "d"] 

实现这种合并的最佳方法应该是什么?

求出两个数组的长度之比,longest.length/shortest.length然后从最长的数组中取那么多,每个最短的数组都取那么多。

let array1 = ["a", "b", "c", "d", "e"];
let array2 = [1, 2];

const evenDistribute = (array1, array2) => {
  const longest = array1.length > array2.length ? array1 : array2;
  const shortest = array1.length > array2.length ? array2 : array1;
  const ratio = Math.floor(longest.length / shortest.length);
  const results = [];
  for (let i = 0; i < shortest.length; i++) {
    for (let j = 0; j < ratio; j++) {
      results.push(longest[i * ratio + j]);
    }
    results.push(shortest[i]);
  }
  // Grab any that are left over
  for (let i = longest.length - (longest.length % shortest.length); i < longest.length; i++) {
    results.push(longest[i]);
  }
  return results;
}

console.log(evenDistribute(array1, array2));

我们的想法是根据长数组中的多少项找出您需要混合短数组中的一项。下面的代码是为了演示这个概念。也许您需要针对所有边缘场景稍微调整一下。

let array1 = ["a", "b", "c", "d"];
let array2 = [1, 2];


//Get the long and short arrays and calc the length factor
var [longArray, shortArray] = array1.length >= array2.length ? [array1, array2] : [array2, array1];
let lengthFactor = longArray.length / shortArray.length;


var c = 0
let smallIdx = 0;
let result = longArray.flatMap(item => {

  c++;
  
  if (c % lengthFactor === 0) {
    return [item, shortArray[smallIdx++]]
  }
  else
    return [item];    
})


console.log(result);

您可以获取分发的时间间隔。然后循环遍历第二个数组,使用splice更新第一个数组的具体索引。

function distribute(original, replace) {
  const interval = Math.ceil(original.length / (replace.length + 1));
  replace.forEach((r, i) => original.splice(interval * (i + 1) + i, 0, r))
  console.log(...original)
}

distribute(["a", "b", "c", "d"], [1])
distribute(["a", "b", "c", "d"], [1, 2])
distribute(["a", "b", "c", "d"], [1, 2, 3])
distribute(["a", "b", "c", "d", "e", "f"], [1, 2])
distribute(["a", "b", "c", "d", "e", "f"], [1, 2, 3])

let array1 = ['a', 'b', 'c', 'd', 'e'];
let array2 = [1, 2];

function merge(arr1, arr2) {
    let newArr1 = JSON.parse(JSON.stringify(arr1));
    let newArr2 = JSON.parse(JSON.stringify(arr2));
    [newArr1, newArr2] = newArr1.length >= newArr2.length ? [newArr1, newArr2] : [newArr2, newArr1];
    const interval = newArr1.length / newArr2.length;
    newArr2.map((item, index) => {
        newArr1.splice(interval * (index + 1), 0, item);
    })
    return newArr1;
}
console.log(merge(array1, array2));

const mix = (firstArray, secondArray) => {
    const itrArray = firstArray.length > secondArray.length ? firstArray : secondArray;
    const result = [];

    for(let i=0; i<itrArray.length; i++){
        firstArray[i] && result.push(firstArray[i]);
        secondArray[i] && result.push(secondArray[i]);
    }
    return result;
}

console.log(mix([1, 2, 3], [4, 5, 6]));
// [1, 4, 2, 5, 3, 6]
console.log(mix(["h", "a", "c"], [7, 4, 17, 10, 48]));
// ["h", 7, "a", 4, "c", 17, 10, 48]