Reputation: 107
I have two arrays with "tickets" that I need to update every 3 seconds, the problem is that for animation reasons, I can't simply overwrite the first array to be just like the second.
Like this:
let array_1 = [1, 2, 3, 5]; //diff 3, 5
let array_2 = [1, 2, 6, 7]; //diff 6, 7
What I need is to compare the two arrays, remove "3 and 5" and push "6 and 7" to the first array, leaving the first array as follows:
array_1 = [1, 2, 6, 7];
How to accomplish that?
For clarification purposes, I'm currently building a dynamic map that receives new info every few seconds, as objects (which is pain in the ass to compare).
I CANNOT have a third array or overwrite the first one, because doing so will cause the markers to 'blink' on the map, so I must manipulate the first one.
I've used @Andrew Yochum response below to came up with the solution as follows:
let array_1 = [
{serial_number: 'abc', lat: 1, lng: 1},
{serial_number: 'def', lat: 2, lng: 2},
{serial_number: 'ghi', lat: 3, lng: 3},
];
let array_2 = [
{serial_number: 'abc', lat: 1, lng: 1},
{serial_number: 'def', lat: 2, lng: 2},
{serial_number: 'jkl', lat: 4, lng: 4},
{serial_number: 'mno', lat: 5, lng: 5},
];
let compare_1 = JSON.parse(JSON.stringify(array_1));
compare_1 = compare_1.map(el => JSON.stringify(el));
let compare_2 = JSON.parse(JSON.stringify(array_2));
compare_2 = compare_2.map(el => JSON.stringify(el));
let removeArray = [...compare_1.filter(i => !compare_2.includes(i))];
let addArray = [...compare_2.filter(i => !compare_1.includes(i))];
compare_1.forEach((first_el) => {
removeArray.forEach((second_el) => {
if(first_el == second_el){
array_1.splice(compare_1.indexOf(first_el, 1));
}
});
});
addArray.forEach((element) => {
array_1.push(JSON.parse(element));
});
Any way to optimize this?
Upvotes: 0
Views: 67
Reputation: 57
based on what you said "What I need is to compare the two arrays, remove "3 and 5" and push "6 and 7" to the first array":
let array_1 = [1, 2, 3, 5]; //diff 3, 5
let array_2 = [1, 2, 6, 7]; //diff 6, 7
for(var i = 0; i < array_1.length; i++){
if(array_1[i] != array_2[i]){
array_1.splice(i,1,array_2[i]);
}
}
console.log(array_1);
Upvotes: 0
Reputation: 1056
Given your new constraints of needing to edit the original array in-place, and the sample data you provided, here is a fairly optimal solution without the JSON encoding/decoding your solution utilizes. No new arrays or copies are made. It also assumes that the serial_number is a unique key that can be used to dedupe between the arrays.
let array_1 = [
{serial_number: 'abc', lat: 1, lng: 1},
{serial_number: 'def', lat: 2, lng: 2},
{serial_number: 'ghi', lat: 3, lng: 3},
]; //diff 'ghi'
let array_2 = [
{serial_number: 'abc', lat: 1, lng: 1},
{serial_number: 'def', lat: 2, lng: 2},
{serial_number: 'jkl', lat: 4, lng: 4},
{serial_number: 'mno', lat: 5, lng: 5},
]; //diff 'jkl' 'mno'
function containsSerialNumber(array, serial_number) {
for(let i = 0; i < array.length; i++) {
if (array[i].serial_number === serial_number) {
return true;
}
}
}
// removes 'ghi'
for (let i = 0; i < array_1.length; i++) {
if (!containsSerialNumber(array_2, array_1[i].serial_number)) {
array_1.splice(i,1);
i--; // Adjust i down since we just edited in-place
}
}
// add 'jkl' 'mno'
for (let i = 0; i < array_2.length; i++) {
if (!containsSerialNumber(array_1, array_2[i].serial_number))
array_1.push(array_2[i]);
}
Upvotes: 2
Reputation: 524
let array_1 = [1, 2, 3, 5]; //diff 3, 5
let array_2 = [1, 2, 6, 7]; //diff 6, 7
for(var i = 0; i < array_1.length; i++){
if(array_1[i] != array_2[i]){
array_1[i] = array_2[i];
}
}
console.log(array_1);
Upvotes: 0