简体   繁体   中英

How to pre-populate an array with empty values?

I'm trying to populate some data I'm receiving from an API into a chart, and for it to "work properly" I need to make sure that each object in the array has 12 values under the sum property (one value for each month of the year).

The data I receive from the API looks like this:

[
  {
    "sum": {
      "201901": 8,
      "201902": 16,
      "201903": 8,
      "201904": 8,
      /* This project is missing data for month 5 and 6 */
      "201907": 5,
      "201908": 2,
      "201909": 0,
      "201910": 2,
      "201911": 5,
      "201912": 8
    },
    "project": "Project Name 1"
  },
  {
    "sum": {
      "201901": 9,
      "201902": 18,
      "201903": 9,
      "201904": 9,
      "201905": 17,
      "201906": 5,
      "201907": 2,
      "201908": 4,
      /* This project is missing data for month 9, 10, 11, 12 */
    },
    "project": "Project Name 2"
  },
  {
    "sum": {
      "201901": 2,
      "201902": 2,
      "201903": 5,
      "201904": 2,
      "201905": 0,
      "201906": 10,
      "201907": 45,
      "201908": 21,
      "201909": 3,
      "201910": 2,
      "201911": 17,
      "201912": 16
    },
    "project": "Project Name 3"
  }
]

So, as you can see, project 1 and project 2 are missing points for some months, but I still need to populate them with an empty value (example: "201905": 0 , "201906": 0 , etc) because the X-axis in my chart will always be 12 values and it messes things up if the Y-axis does not have 12 values given. So my question is: how would I populate each object to always provide a value for each month of the year?

So far, I'm looping through the data as such:

for (let key in this.chartData) {
    emptyArr.push({
        name: this.chartData[key].project,
        data: Object.values(this.chartData[key].sum),
    });
}

which effectively gives me something to work with:

[
  {
    "name": "Project 1",
    "data": [8, 16, 8, 8, 21, 4, 5, 2, 0, 2, 5, /*Need a "0" here*/]
  },
  {
    "name": "Project 2",
    "data": [9, 18, 9, 9, 17, 5, 2, 4, /*Need 4 more 0's here*/]
  },
  {
    "name": "Project 3",
    "data": [2, 2, 5, 2, 0, 10, 45, 21, 3, 2, 17, 16]
  }
]

You could take an empty sum object and assign the values to a new object.

 var data = [{ sum: { 201901: 8, 201902: 16, 201903: 8, 201904: 8, 201907: 5, 201908: 2, 201909: 0, 201910: 2, 201911: 5, 201912: 8 }, project: "Project Name 1" }, { sum: { 201901: 9, 201902: 18, 201903: 9, 201904: 9, 201905: 17, 201906: 5, 201907: 2, 201908: 4 }, project: "Project Name 2" }, { sum: { 201901: 2, 201902: 2, 201903: 5, 201904: 2, 201905: 0, 201906: 10, 201907: 45, 201908: 21, 201909: 3, 201910: 2, 201911: 17, 201912: 16 }, project: "Project Name 3" }], empty = { 201901: 0, 201902: 0, 201903: 0, 201904: 0, 201905: 0, 201906: 0, 201907: 0, 201908: 0, 201909: 0, 201910: 0, 201911: 0, 201912: 0 }, empty = { 201901: 0, 201902: 0, 201903: 0, 201904: 0, 201905: 0, 201906: 0, 201907: 0, 201908: 0, 201909: 0, 201910: 0, 201911: 0, 201912: 0 }, result = data.map(({ sum, ...rest }) => ({ sum: { ...empty, ...sum }, ...rest })); console.log(result); 
 .as-console-wrapper { max-height: 100% !important; top: 0; } 

If you define an object with all the 12 keys , such as:

const normalizedSum = {
  "201901": 0,
  "201902": 0,
  "201903": 0,
  "201904": 0,
  "201905": 0,
  "201906": 0,
  "201907": 0,
  "201908": 0,
  "201909": 0,
  "201910": 0,
  "201911": 0,
  "201912": 0
};

Then, you can use Array.map() on your input array like this:

input.map(({sum, project}) => ({sum: {...normalizedSum, ...sum}, project}));

Full Example:

 const input = [{"sum":{"201901":8,"201902":16,"201903":8,"201904":8,"201907":5,"201908":2,"201909":0,"201910":2,"201911":5,"201912":8},"project":"Project Name 1"},{"sum":{"201901":9,"201902":18,"201903":9,"201904":9,"201905":17,"201906":5,"201907":2,"201908":4,},"project":"Project Name 2"},{"sum":{"201901":2,"201902":2,"201903":5,"201904":2,"201905":0,"201906":10,"201907":45,"201908":21,"201909":3,"201910":2,"201911":17,"201912":16},"project":"Project Name 3"}]; const normalizedSum = { "201901": 0, "201902": 0, "201903": 0, "201904": 0, "201905": 0, "201906": 0, "201907": 0, "201908": 0, "201909": 0, "201910": 0, "201911": 0, "201912": 0 }; let res = input.map( ({sum, project}) => ({sum: {...normalizedSum, ...sum}, project}) ); console.log(res); 
 .as-console {background-color:black !important; color:lime;} .as-console-wrapper {max-height:100% !important; top:0;} 

What you can do is make a template object which has all the 12 months with default values of 0 . Then go through the sum items and if they have the matching date key then set it to the value of the key in sum :

for (let key in chartData) {
  // template object holding 0s
  let data = { "201901": 0, "201902": 0, "201903": 0, "201904": 0, "201905": 0, "201906": 0, "201907": 0, "201908": 0, "201909": 0, "201910": 0, "201911": 0, "201912": 0 };
  // For each key that exist in the sum object populate data with that value
  for (let month in chartData[key].sum) data[month] = chartData[key].sum[month];

  emptyArr.push({
    name: chartData[key].project,
    data: Object.values(data), // Now you can do the same thing you where doing before
  });
}

Here is a full example:

 let chartData = [ { "sum": { "201901": 8, "201902": 16, "201903": 8, "201904": 8, /* This project is missing data for month 5 and 6 */ "201907": 5, "201908": 2, "201909": 0, "201910": 2, "201911": 5, "201912": 8 }, "project": "Project Name 1" }, { "sum": { "201901": 9, "201902": 18, "201903": 9, "201904": 9, "201905": 17, "201906": 5, "201907": 2, "201908": 4, /* This project is missing data for month 9, 10, 11, 12 */ }, "project": "Project Name 2" }, { "sum": { "201901": 2, "201902": 2, "201903": 5, "201904": 2, "201905": 0, "201906": 10, "201907": 45, "201908": 21, "201909": 3, "201910": 2, "201911": 17, "201912": 16 }, "project": "Project Name 3" } ]; let emptyArr = [] for (let key in chartData) { let data = { "201901": 0, "201902": 0, "201903": 0, "201904": 0, "201905": 0, "201906": 0, "201907": 0, "201908": 0, "201909": 0, "201910": 0, "201911": 0, "201912": 0 }; for (let month in chartData[key].sum) data[month] = chartData[key].sum[month]; emptyArr.push({ name: chartData[key].project, data: Object.values(data), }); } console.log(emptyArr); 

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM