JavaScript объединение двух многомерных массивов в уникальные массивы - PullRequest
1 голос
/ 21 июня 2020

Я пытаюсь отсортировать данные, которые выглядят так:

{
    "Params": [
        ["section", "North"],
        ["monitor", "Single Monitor"],
        ["section", "North"],
        ["monitor", "Dual Monitor"]
    ]
}

На что-то похожее на это:

{
    "section": [
        "North"
    ],
    "monitor": [
        "Single Monitor",
        "Dual Monitor"
    ]
}

Но у меня в настоящее время возникают проблемы, я пробовал несколько разных вещей, таких как объединение массивов вместе в al oop, или даже использование функции uniq loda sh, но каждый раз я получаю нежелательный результат.

Заранее благодарим за любую помощь

Ответы [ 4 ]

2 голосов
/ 21 июня 2020

Вы можете агрегировать свой массив массивов, используя array.reduce:

let obj = {
    "Params": [
        ["section", "North"],
        ["monitor", "Single Monitor"],
        ["section", "North"],
        ["monitor", "Dual Monitor"]
    ]
}

let result = obj.Params.reduce((acc,cur) => {
   let [key,value] = cur;
   if(!acc[key]){
      acc[key] = [];
   }
   if(!acc[key].includes(value)){
      acc[key].push(value);
   }
   return acc;
}, {});

console.log(result);
0 голосов
/ 21 июня 2020

Вы можете превратить метод reduce () в функцию groupBy следующим образом

let obj = {
  "Params": [
    ["section", "North"],
    ["monitor", "Single Monitor"],
    ["section", "North"],
    ["monitor", "Dual Monitor"]
  ]
};

const res = obj.Params.reduce((acc, [key, val]) => {
  acc[key] = acc[key] || [];
  if (!acc[key].includes(val)) {
    acc[key].push(val);
  }
  return acc;
}, {});
console.log(res);
0 голосов
/ 21 июня 2020

Вы можете использовать _.groupBy() _.head() (первый элемент каждой пары) для группировки элементов. Затем используйте _.mapValues() для итерации каждой группы, сопоставьте ее, чтобы получить элемент _.last(), и используйте _.uniq(), чтобы получить только уникальные значения:

const data = {"Params":[["section","North"],["monitor","Single Monitor"],["section","North"],["monitor","Dual Monitor"]]};

const result = _.mapValues(
  _.groupBy(data.Params, _.head), // group by the first item
  g => _.uniq(_.map(g, _.last)) // map each group to the last item, and get unique values
);

console.log(result);
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.15/lodash.js"></script>

С помощью loda sh lodash / fp вы можете сгенерировать функцию, используя _.flow(), которая делает то же самое:

const { flow, groupBy, head, mapValues, map, last, uniq } = _;

const fn = flow(
  groupBy(head),
  mapValues(flow(
    map(last),
    uniq
  ))
);

const data = {"Params":[["section","North"],["monitor","Single Monitor"],["section","North"],["monitor","Dual Monitor"]]};

const result = fn(data.Params);

console.log(result);
<script src='https://cdn.jsdelivr.net/g/lodash@4(lodash.min.js+lodash.fp.min.js)'></script>
0 голосов
/ 21 июня 2020

Здесь необходимо выполнить количество операций. Вы можете использовать reduce, чтобы сгруппировать ключевые данные. Поскольку у вас есть только формат массива пар ключ-значение, поэтому в reduce я деструктурировал его, указав [k,v], указывая ключ и значение. Затем, чтобы удалить повторяющиеся значения, я использовал Set.

var data={
    "Params": [
        ["section", "North"],
        ["monitor", "Single Monitor"],
        ["section", "North"],
        ["monitor", "Dual Monitor"]
    ]
};

var result = data.Params.reduce((a,[k, v])=>(a[k] = [...(a[k] || []), v], a[k] = [...new Set(a[k])], a),{});

console.log(result);
...