Как добавить пару ключ-значение в массив в Javascript / Jquery

#javascript #jquery #arrays

#javascript #jquery #массивы

Вопрос:

У меня есть 2 массива, как показано ниже

 var dataSource = [
{location: "France", January: 79, February: 81, March: 23},  
{location: "Germany", January: 98, February: 83},
{location: "Japan", January: 96, March: 11} ];

var Months = ["January","February","March"];
  

Я хочу перебрать каждый объект в dataSource и проверить, существуют ли все значения Months в каждом объекте dataSource . Если значение не существует в dataSource , добавьте это значение в dataSource со значением = 100

пример: в местоположении Germany месяца «Март» не существует, поэтому мне нужно ввести ключ и значение March : 100

в конце dataSource должно быть как показано ниже

 var dataSource = [
{location: "France", January: 79, February: 81, March: 23},  
{location: "Germany", January: 98, February: 83, March: 100},
{location: "Japan", January: 96, February: 100, March: 11} ];
  

Я перепробовал много решений из предыдущих потоков, но я не получаю точного результата, который я хочу. Вот некоторые из моих идей

 var dataSource = [
{location: "France", January: 79, February: 81, March: 23},  
{location: "Germany", January: 98, February: 83},
{location: "Japan", January: 96, March: 11} ];

var Months = ["January","February","March"];

dataSource.forEach(function(element) {
Months.forEach(function(item) {
  if (!(item in element)) {
//Object.assign(dataSource, {item: 100}); 
//dataSource = {...dataSource, ...{item: 100}}
dataSource.push({item: 100});
  }
});
});

console.log(dataSource);  

Спасибо за ваши предложения.

Ответ №1:

Вы можете использовать Array.map() для итерации dataSource массива. Используйте internal Array.reduce() для перебора месяцев и добавления недостающих месяцев к текущему объекту:

 const dataSource = [{"location":"France","January":79,"February":81,"March":23},{"location":"Germany","January":98,"February":83},{"location":"Japan","January":96,"March":11}];
const Months = ["January","February","March"];

const result = dataSource.map(o =>
  Months.reduce((obj, m) => m in obj ? obj : { ...obj, [m]: 100 }, o)
);

console.log(result);  

Ответ №2:

Вы можете перебирать источники и месяцы, устанавливая месяцы в источниках как значение, которое у них уже есть, или по умолчанию равное 100.

 var dataSource = [{
    location: "France",
    January: 79,
    February: 81,
    March: 23
  },
  {
    location: "Germany",
    January: 98,
    February: 83
  },
  {
    location: "Japan",
    January: 96,
    March: 11
  }
];

var Months = ["January", "February", "March"];

dataSource.forEach(function(element){
  Months.forEach(function(month){
    if (element[month] === undefined) element[month] = 100;
  });
});

console.log(dataSource);  

Комментарии:

1. Это изменит явное значение 0 на 100 .

2. @Barmar приятная уловка, исправлена.

Ответ №3:

Или же вы можете создать хэш с результирующими месяцами и их значениями, которые вы можете использовать напрямую, назначив каждый объект вашего массива поверх него. Таким образом, вы можете обрабатывать N количество входных данных (массивов) с одним и тем же хэшем.

Пример результирующего хэша: {January: 100, February: 100, March: 100}

И затем вы можете делать это N количество раз:

 dataSource1.map(d => ({...hash, ...d}));
dataSource2.map(d => ({...hash, ...d}));
dataSource3.map(d => ({...hash, ...d}));
  

Вот пример:

 let dataSource = [{"location":"France","January":79,"February":81,"March":23},{"location":"Germany","January":98,"February":83},{"location":"Japan","January":96,"March":11}],
    Months = ["January","February","March"],
    hash = Months.reduce((r, e) => ({...r, [e]: 100}), {}),
    res = dataSource.map(d => ({...hash, ...d}));
    
console.log('This is your hash: ', hash); //This is the hash generated one time
console.log('This is your result: ', res); //this is the result against that input  

Ответ №4:

Возможно, это может вам немного помочь. Просто запустите test() инструменты разработчика или что-то еще и посмотрите на консоль.вывод журнала

обратите внимание на uniqueKeys объект, поскольку вокруг него сосредоточена основная логика, и на материале hasOwnProperty

 function test() {

    var uniqueKeys = {location: ''};                        //default to have location set
    var Months = ['January', 'February', 'March'];

    for (var i = 0; i < Months.length; i  ) {
        uniqueKeys[Months[i]] = '';                     //just populate the object from the array to use soon
    }


    for (var i = 0; i < dataSource.length; i  ) {




        var validObject = true;
        Object.keys(uniqueKeys).forEach((e,j) => {

            if (dataSource[i].hasOwnProperty(e) === false) {
                validObject = false;
            }

        });

        if (validObject === false) {

            console.log('add to', dataSource[i], 'to balance it out');

        }
    }
}
  

надеюсь, это поможет некоторым
~ приветствия

Ответ №5:

Может быть это короткое решение, которое перебирает месяцы и проверяет, присутствует ли этот месяц в каждой записи для источника данных. Если нет, то добавьте значение по умолчанию, 100 в вашем случае

 for(i=0;i<dataSource.length;i  ){
        for(j=0;j<Months.length;j  ){
            if(Months[j] in dataSource[i]){
            }
            else{
                dataSource[i][Months[j]] = 100;
            }   
        }
    }