Reputation: 681
I have two array of objects. Something like this:
var arrayA = [
{
type: 'card',
id: 1
},
{
type: 'card',
id: 2
},
{
type: 'card',
id: 3
},
{
type: 'card',
id: 4
},
{
type: 'card',
id: 5
},
];
var arrayB = [
{
type: 'pro-tip',
id: 10
},
{
type: 'pro-tip',
id: 11
},
];
I want to merge these two arrays of objects, but on a specific order. Basically, what I want is that, after each N number of elements from arrayA
, I want to add one element from arrayB
. If N == 2
The final array would look like this:
var finalArray = [
{
type: 'card',
id: 1
},
{
type: 'card',
id: 2
},
{
type: 'pro-tip',
id: 10
},
{
type: 'card',
id: 3
},
{
type: 'card',
id: 4
},
{
type: 'pro-tip',
id: 11
},
{
type: 'card',
id: 5
},
];
Probably it is not difficult to do something like this, but I'm looking for the most elegant way to build a helper function to do that.
Edit:
Here's the function I created. It seems like it works, but there might be a simpler way to do it:
function mergeWithSteps( arrayA, arrayB, nSteps, nElementsToAdd ) {
var finalArray = [],
stepsCount = 0,
elementsToAddCount = 0,
arrayBNumberOfElements = arrayB.length;
arrayA.forEach( function( obj ) {
finalArray.push( obj );
stepsCount++;
if( stepsCount == nSteps && elementsToAddCount < arrayBNumberOfElements ) {
finalArray.push( arrayB[ elementsToAddCount ] );
elementsToAddCount++;
stepsCount = 0;
}
} );
return finalArray;
}
Upvotes: 0
Views: 73
Reputation: 2621
You can use reduce
if the initial array is not to modify.
const arrayA = [
{
type: 'card',
id: 1
},
{
type: 'card',
id: 2
},
{
type: 'card',
id: 3
},
{
type: 'card',
id: 4
},
{
type: 'card',
id: 5
},
];
const arrayB = [
{
type: 'pro-tip',
id: 10
},
{
type: 'pro-tip',
id: 11
},
];
const res = arrayA.reduce((acc, a, i) => {
const b = arrayB[(i + 1) / 2 - 1];
return [...acc, a, ...(b ? [b] : [])];
}, []);
console.log(res);
Upvotes: 0
Reputation: 4392
Here's my iterative solution using for
countA = arrayA.length;
countB = arrayB.length;
merged = [];
for (var i = 0, j = 0, m = 0; i < countA; i ++, m ++) {
if (i > 0 && i%2 == 0 && typeof arrayB[j] !== 'undefined') {
merged[m] = arrayB[j];
j ++;
m ++;
}
merged[m] = arrayA[i];
}
// if you'd like to place all remaining arrayB elements after arrayA is exhausted
if (countB > j) {
for (i = j; i < countB; i++, m ++) {
merged[m] = arrayB[i];
}
}
Upvotes: 0
Reputation: 386654
You could use Array#slice
for inserting the wanted item and iterate arrayB
from the end, because every splicing changes the indices after the insertation index.
var arrayA = [{ type: 'card', id: 1 }, { type: 'card', id: 2 }, { type: 'card', id: 3 }, { type: 'card', id: 4 }, { type: 'card', id: 5 }],
arrayB = [{ type: 'pro-tip', id: 10 }, { type: 'pro-tip', id: 11 }],
place = 2,
i = arrayB.length;
while (i) {
arrayA.splice(i * place, 0, arrayB[--i]);
}
console.log(arrayA);
.as-console-wrapper { max-height: 100% !important; top: 0; }
Upvotes: 3