3

I have two big arrays I want to compare both arrays and add missing data from arrayOne to arrayTwo

this is my some of the data

const arrayOne = [
  {
    id: "This Year",
    data: [
      { x: "01-02", y: "81" },
      { x: "01-03", y: "361" },
      { x: "01-04", y: "64" },
      { x: "01-05", y: "169" },
      { x: "01-06", y: "9" },
      { x: "01-07", y: "100" },
      { x: "01-08", y: "144" },
      { x: "01-09", y: "81" },
      { x: "01-10", y: "256" },
      { x: "01-11", y: "81" },
      { x: "01-12", y: "144" },
      { x: "01-13", y: "144" },
      { x: "01-14", y: "225" },
      { x: "01-15", y: "289" },
      { x: "01-16", y: "81" },
      { x: "01-17", y: "64" },
      { x: "01-18", y: "64" },
      { x: "01-19", y: "121" },
      { x: "01-20", y: "25" },
      { x: "01-21", y: "49" },
      { x: "01-22", y: "16" },
      { x: "01-23", y: "49" },
      { x: "01-24", y: "196" },
      { x: "01-25", y: "16" },
      { x: "01-26", y: "25" },
      { x: "01-27", y: null },
      { x: "01-28", y: "144" },
      { x: "01-29", y: "100" },
      { x: "01-30", y: "64" },
      { x: "01-31", y: "144" },
      { x: "02-01", y: "100" },
      { x: "02-02", y: "100" },
      { x: "02-03", y: "49" },
    ],
  },
];

const arrayTwo = [
  {
    id: "This Year",
    data: [
      { x: "01-02", y: "64" },
      { x: "01-03", y: "25" },
      { x: "01-04", y: "25" },
      { x: "01-05", y: "169" },
      { x: "01-15", y: "64" },
      { x: "01-16", y: "121" },
      { x: "01-17", y: "49" },
      { x: "01-18", y: "81" },
      { x: "01-19", y: "49" },
    ],
  },
];

I have tried to map it and compare it with respect to x but i am not able to achieve desirable output

arrayOne[0].data.map((date, index) => {
    arrayTwo[0].data.map((newDate, newIndex) => {
  if (date.x !== newDate.x) {
      arrayTwo[0].data.push({x:date.x, y: null })
    }
    });
  });

I want to check if data is missing from arrayTwo[data] if it is missing then add that data from arrayOne[data] (i.e. take the object with its x-value but set the y-value to null)

Desired output:

[
  {
    "id":"This Year",
    "data":[
      {"x":"01-02", "y":"64"},
      {"x":"01-03", "y":"25"},
      {"x":"01-04", "y":"25"},
      {"x":"01-05", "y":"169"},
      {"x":"01-06", "y":null},
      {"x":"01-07", "y":null},
      {"x":"01-08", "y":null},
      {"x":"01-09", "y":null},
      {"x":"01-10", "y":null},
      {"x":"01-11", "y":null},
      {"x":"01-12", "y":null},
      {"x":"01-13", "y":null},
      {"x":"01-14", "y":null},
      {"x":"01-15", "y":"64"},
      {"x":"01-16", "y":"121"},
      {"x":"01-17", "y":"49"},
      {"x":"01-18", "y":"81"},
      {"x":"01-19", "y":"49"},
      {"x":"01-20", "y":null},
      {"x":"01-21", "y":null},
      {"x":"01-22", "y":null},
      {"x":"01-23", "y":null},
      {"x":"01-24", "y":null},
      {"x":"01-25", "y":null},
      {"x":"01-26", "y":null},
      {"x":"01-27", "y":null},
      {"x":"01-28", "y":null},
      {"x":"01-29", "y":null},
      {"x":"01-30", "y":null},
      {"x":"01-31", "y":null},
      {"x":"02-01", "y":null},
      {"x":"02-02", "y":null},
      {"x":"02-03", "y":null}
    ]
  }
]
6
  • And the question/problem is? Commented May 12, 2020 at 11:51
  • @Andreas I am not able to acheive it/ Commented May 12, 2020 at 11:53
  • what is the key for comparison or do you want to check the whole object agains the whole object Commented May 12, 2020 at 11:55
  • In your output do you want {"x": "01-19", "y": "121"} from arrayOne, or do you want the following which exists in arrayTwo {"x": "01-19", "y": "49"}? I believe the latter from reading your question and @EugenSunic's answer is doing the opposite (would be an easy fix to reverse the behaviour) Commented May 12, 2020 at 15:44
  • 1
    Ok, so neither of the answers below currently give that behaviour. I now added the desired output to your question, please confirm that is correct. If so, my updated answer (2nd example) now gives that desired output. Commented May 12, 2020 at 17:18

2 Answers 2

2

You can do it like this:

  • create an object (objOne) from arrayOne[0].data using reduce
  • overwrite any property of the objOne if the key is present in arrayTwo[0].data, again using reduce and using objOne as the initial value.
  • convert this objOne to an array with Object.values(objOne) and then set that as the property of arrayTwo[0].data

Time complexity should be O(n + m) for the two reduce functions (where n and m are the length of the two arrays). (Should be faster than using find for every element in one of the arrays)

Key part of the code:

const objOne = arrayOne[0].data.reduce((aggObj, item) => {
  aggObj[item.x] = item;  
  return aggObj;
}, {});

const mergedObjOutput = arrayTwo[0].data.reduce((aggObj, item) => {
  aggObj[item.x] = item;  
  return aggObj;
}, objOne)

const mergedFinalOutput = [...arrayTwo];
mergedFinalOutput[0].data = Object.values(mergedObjOutput);

console.log(mergedFinalOutput);

Full demo:

const arrayOne = [
  {
    id: "This Year",
    data: [
      { x: "01-02", y: "81" },
      { x: "01-03", y: "361" },
      { x: "01-04", y: "64" },
      { x: "01-05", y: "169" },
      { x: "01-06", y: "9" },
      { x: "01-07", y: "100" },
      { x: "01-08", y: "144" },
      { x: "01-09", y: "81" },
      { x: "01-10", y: "256" },
      { x: "01-11", y: "81" },
      { x: "01-12", y: "144" },
      { x: "01-13", y: "144" },
      { x: "01-14", y: "225" },
      { x: "01-15", y: "289" },
      { x: "01-16", y: "81" },
      { x: "01-17", y: "64" },
      { x: "01-18", y: "64" },
      { x: "01-19", y: "121" },
      { x: "01-20", y: "25" },
      { x: "01-21", y: "49" },
      { x: "01-22", y: "16" },
      { x: "01-23", y: "49" },
      { x: "01-24", y: "196" },
      { x: "01-25", y: "16" },
      { x: "01-26", y: "25" },
      { x: "01-27", y: null },
      { x: "01-28", y: "144" },
      { x: "01-29", y: "100" },
      { x: "01-30", y: "64" },
      { x: "01-31", y: "144" },
      { x: "02-01", y: "100" },
      { x: "02-02", y: "100" },
      { x: "02-03", y: "49" },
    ],
  },
];

const arrayTwo = [
  {
    id: "This Year",
    data: [
      { x: "01-02", y: "64" },
      { x: "01-03", y: "25" },
      { x: "01-04", y: "25" },
      { x: "01-05", y: "169" },
      { x: "01-15", y: "64" },
      { x: "01-16", y: "121" },
      { x: "01-17", y: "49" },
      { x: "01-18", y: "81" },
      { x: "01-19", y: "49" },
    ],
  },
];

const objOne = arrayOne[0].data.reduce((aggObj, item) => {
  aggObj[item.x] = item;  
  return aggObj;
}, {});

const mergedObjOutput = arrayTwo[0].data.reduce((aggObj, item) => {
  aggObj[item.x] = item;  
  return aggObj;
}, objOne)

const mergedFinalOutput = [...arrayTwo];
mergedFinalOutput[0].data = Object.values(mergedObjOutput);

console.log(mergedFinalOutput);
.as-console-wrapper { max-height: 100% !important; top: 0; }

UPDATE

If you really want your output like this (from your clarification in the comments under your question):

[
  {
    "id":"This Year",
    "data":[
      {"x":"01-02", "y":"64"},
      {"x":"01-03", "y":"25"},
      {"x":"01-04", "y":"25"},
      {"x":"01-05", "y":"169"},
      {"x":"01-06", "y":null},
      {"x":"01-07", "y":null},
      {"x":"01-08", "y":null},
      {"x":"01-09", "y":null},
      {"x":"01-10", "y":null},
      {"x":"01-11", "y":null},
      {"x":"01-12", "y":null},
      {"x":"01-13", "y":null},
      {"x":"01-14", "y":null},
      {"x":"01-15", "y":"64"},
      {"x":"01-16", "y":"121"},
      {"x":"01-17", "y":"49"},
      {"x":"01-18", "y":"81"},
      {"x":"01-19", "y":"49"},
      {"x":"01-20", "y":null},
      {"x":"01-21", "y":null},
      {"x":"01-22", "y":null},
      {"x":"01-23", "y":null},
      {"x":"01-24", "y":null},
      {"x":"01-25", "y":null},
      {"x":"01-26", "y":null},
      {"x":"01-27", "y":null},
      {"x":"01-28", "y":null},
      {"x":"01-29", "y":null},
      {"x":"01-30", "y":null},
      {"x":"01-31", "y":null},
      {"x":"02-01", "y":null},
      {"x":"02-02", "y":null},
      {"x":"02-03", "y":null}
    ]
  }
]

Then this is the demo:

const arrayOne = [
  {
    id: "This Year",
    data: [
      { x: "01-02", y: "81" },
      { x: "01-03", y: "361" },
      { x: "01-04", y: "64" },
      { x: "01-05", y: "169" },
      { x: "01-06", y: "9" },
      { x: "01-07", y: "100" },
      { x: "01-08", y: "144" },
      { x: "01-09", y: "81" },
      { x: "01-10", y: "256" },
      { x: "01-11", y: "81" },
      { x: "01-12", y: "144" },
      { x: "01-13", y: "144" },
      { x: "01-14", y: "225" },
      { x: "01-15", y: "289" },
      { x: "01-16", y: "81" },
      { x: "01-17", y: "64" },
      { x: "01-18", y: "64" },
      { x: "01-19", y: "121" },
      { x: "01-20", y: "25" },
      { x: "01-21", y: "49" },
      { x: "01-22", y: "16" },
      { x: "01-23", y: "49" },
      { x: "01-24", y: "196" },
      { x: "01-25", y: "16" },
      { x: "01-26", y: "25" },
      { x: "01-27", y: null },
      { x: "01-28", y: "144" },
      { x: "01-29", y: "100" },
      { x: "01-30", y: "64" },
      { x: "01-31", y: "144" },
      { x: "02-01", y: "100" },
      { x: "02-02", y: "100" },
      { x: "02-03", y: "49" },
    ],
  },
];

const arrayTwo = [
  {
    id: "This Year",
    data: [
      { x: "01-02", y: "64" },
      { x: "01-03", y: "25" },
      { x: "01-04", y: "25" },
      { x: "01-05", y: "169" },
      { x: "01-15", y: "64" },
      { x: "01-16", y: "121" },
      { x: "01-17", y: "49" },
      { x: "01-18", y: "81" },
      { x: "01-19", y: "49" },
    ],
  },
];

const objOne = arrayOne[0].data.reduce((aggObj, item) => {
  aggObj[item.x] = {...item, y: null};  
  return aggObj;
}, {});

const mergedObjOutput = arrayTwo[0].data.reduce((aggObj, item) => {
  aggObj[item.x] = item;  
  return aggObj;
}, objOne)

const mergedFinalOutput = [...arrayTwo];
mergedFinalOutput[0].data = Object.values(mergedObjOutput);

console.log(mergedFinalOutput);
.as-console-wrapper { max-height: 100% !important; top: 0; }

Sign up to request clarification or add additional context in comments.

Comments

1

Try something like this:

Loop through the elements, if they aren't found in the first array add them to the second array

const arrayOne = [
  {
    id: "This Year",
    data: [
      { x: "01-02", y: "81" },
      { x: "01-03", y: "361" },
      { x: "01-04", y: "64" },
      { x: "01-05", y: "169" },
      { x: "01-06", y: "9" },
      { x: "01-07", y: "100" },
      { x: "01-08", y: "144" },
      { x: "01-09", y: "81" },
      { x: "01-10", y: "256" },
      { x: "01-11", y: "81" },
      { x: "01-12", y: "144" },
      { x: "01-13", y: "144" },
      { x: "01-14", y: "225" },
      { x: "01-15", y: "289" },
      { x: "01-16", y: "81" },
      { x: "01-17", y: "64" },
      { x: "01-18", y: "64" },
      { x: "01-19", y: "121" },
      { x: "01-20", y: "25" },
      { x: "01-21", y: "49" },
      { x: "01-22", y: "16" },
      { x: "01-23", y: "49" },
      { x: "01-24", y: "196" },
      { x: "01-25", y: "16" },
      { x: "01-26", y: "25" },
      { x: "01-27", y: null },
      { x: "01-28", y: "144" },
      { x: "01-29", y: "100" },
      { x: "01-30", y: "64" },
      { x: "01-31", y: "144" },
      { x: "02-01", y: "100" },
      { x: "02-02", y: "100" },
      { x: "02-03", y: "49" }
    ]
  }
];

const arrayTwo = [
  {
    id: "This Year",
    data: [
      { x: "01-02", y: "64" },
      { x: "01-03", y: "25" },
      { x: "01-04", y: "25" },
      { x: "01-05", y: "169" },
      { x: "01-15", y: "64" },
      { x: "01-16", y: "121" },
      { x: "01-999", y: "49" },
      { x: "01-18", y: "81" },
      { x: "01-19", y: "49" }
    ]
  }
];

console.log(arrayOne);
arrayTwo[0].data.forEach(obj => {
  const found = arrayOne[0].data.find(obj2 => obj2.x === obj.x);
  if (!found) {
    arrayOne[0].data.push(obj);
  }
});

console.log(arrayOne);

1 Comment

From the question @Rizwan Ahmed Shivalli said "I want to check if data is missing from arrayTwo[data] if it is missing then add that data from arrayOne[data]" but you have the following in your output: {"x": "01-19", "y": "121"} and this is clearly from arrayOne, while the following exists in arrayTwo {"x": "01-19", "y": "49"} and so should (if I understand the question correctly) be present in the output

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.