簡體   English   中英

如何將具有相同屬性的對象合並到一個數組中?

[英]How to merge objects with the same properties into a single Array?

我正在收到下一個數據

    [
      { id: "1", name: "test1", rName: "the1" },
      { id: "1", name: "test1", rName: "the2" },
      { id: "1", name: "test1", rName: "the3" },
      { id: "2", name: "test2", rName: "the1" },
      { id: "2", name: "test2", rName: "the2" },
      { id: "3", name: "test3", rName: "the1" }
    ]

我想通過id合並它並將rName推入一個數組以獲得這個結構

    [
      { id: "1", name: "test1", rName: ["the1", "the2","the3"] },
      { id: "2", name: "test2", rName: ["the1", "the2"] },
      { id: "3", name: "test3", rName: ["the1"] }
    ]

我認為這樣做會減少,但沒有成功,如果有人能指出我正確的方向,將不勝感激。

這是一個非常簡單的數據重新格式化案例。 代碼如下。

 var data = [ { id: "1", name: "test1", rName: "the1" }, { id: "1", name: "test1", rName: "the2" }, { id: "1", name: "test1", rName: "the3" }, { id: "2", name: "test2", rName: "the1" }, { id: "2", name: "test2", rName: "the2" }, { id: "3", name: "test3", rName: "the1" } ]; var reduced = Object.values(data.reduce(function(accumulator, element) { if (!accumulator[element.id]) { accumulator[element.id] = { id: element.id, name: element.name, rName: [] }; } accumulator[element.id].rName.push(element.rName); return accumulator; }, {})); console.log(reduced); 

累加器檢查按element.id中的鍵是否存在於累加器中。 如果沒有,則創建它。 然后它在現有堆棧上推送新的rName 然后使用Object.values()將轉換返回到數組。

您可以使用reducefind如下:

在reduce accumulator ,檢查是否已存在與正在迭代的當前項具有相同id的項。 如果是,請將當前項的rName推送到rName數組。 否則,將新項目推送到accumulator

 var data = [ { id: "1", name: "test1", rName: "the1" }, { id: "1", name: "test1", rName: "the2" }, { id: "1", name: "test1", rName: "the3" }, { id: "2", name: "test2", rName: "the1" }, { id: "2", name: "test2", rName: "the2" }, { id: "3", name: "test3", rName: "the1" } ]; const newArray = data.reduce((acc, {id,name,rName}) => { const existing = acc.find(a => a.id == id); if (existing) existing["rName"].push(rName); else acc.push({id,name,rName: [rName]}) return acc }, []); console.log(newArray) 

這是一個代碼高爾夫的答案。 (從@Sébastien的回答中得到了想法):

 var data = [ { id: "1", name: "test1", rName: "the1" }, { id: "1", name: "test2", rName: "the2" }, { id: "1", name: "test2", rName: "the3" }, { id: "2", name: "test2", rName: "the1" }, { id: "2", name: "test1", rName: "the2" }, { id: "3", name: "test3", rName: "the1" } ] const anotherArray = Object.values(data.reduce((acc, {id,name,rName}) => ((acc[id] = acc[id] || {id,name,rName:[]})["rName"].push(rName), acc), {})); console.log(anotherArray) 

純ES6

let result = obj.reduce((acc, item) => {
  let found = acc.find(i => i.id === item.id);
  found ? (found.rName = [...found.rName, item.rName]) : (acc = [...acc, { ...item, rName: [item.rName] }]);
  return acc;
}, []);

如果每個id都可以確定唯一的name ,那么這將起作用:

let data = [
  { id: "1", name: "test1", rName: "the1" },
  { id: "1", name: "test1", rName: "the2" },
  { id: "1", name: "test1", rName: "the3" },
  { id: "2", name: "test2", rName: "the1" },
  { id: "2", name: "test2", rName: "the2" },
  { id: "3", name: "test3", rName: "the1" }
];

let result = [];

for (let item of data) 
{
    const index = result.findIndex(i => i.id === item.id);
    if (index < 0) {
        result.push({ id: item.id, name: item.name, rName: [item.rName] });
    }
    else {
        result[index].rName.push(item.rName);
    }
}

請注意,當以下數據接受時,這將不起作用:

[
  { id: "1", name: "test1", rName: "the1" },
  { id: "1", name: "test2", rName: "the2" },
  { id: "1", name: "test2", rName: "the3" },
  { id: "2", name: "test2", rName: "the1" },
  { id: "2", name: "test1", rName: "the2" },
  { id: "3", name: "test3", rName: "the1" }
]

如果你堅持使用'reduce'方法,你可以這樣做:

var arr = [
        { id: "1", name: "test1", rName: "the1" },
        { id: "1", name: "test1", rName: "the2" },
        { id: "1", name: "test1", rName: "the3" },
        { id: "2", name: "test2", rName: "the1" },
        { id: "2", name: "test2", rName: "the2" },
        { id: "3", name: "test3", rName: "the1" }
    ]
    var arr1 = arr.reduce(function (a1, a2) {
        if (a1 instanceof Array) {
            let lastItem = a1[a1.length - 1]
            if (lastItem.id == a2.id) {
                lastItem.rName.push(a2.rName)
            } else {
                a1.push({ ...a2, rName: [a2.rName] })
            }
            return a1
        } else {
            let result = []
            if (a1.id == a2.id) {
                result.push({ ...a1, rName: [a1.rName, a2.rName] })
            } else {
                result.push({ ...a1, rName: [a1, rName] })
                result.push({ ...a2, rName: [a2, rName] })
            }
            return result

        }

    })
    console.log(JSON.stringify(arr1))

但我認為你應該這樣做,因為代碼更清晰:

var arr = [
    { id: "1", name: "test1", rName: "the1" },
    { id: "1", name: "test1", rName: "the2" },
    { id: "1", name: "test1", rName: "the3" },
    { id: "2", name: "test2", rName: "the1" },
    { id: "2", name: "test2", rName: "the2" },
    { id: "3", name: "test3", rName: "the1" }
]
var map = new Map()
arr.forEach(function(item){
    if(map.has(item.id)){
        map.get(item.id).rName.push(item.rName)
    }else{
        map.set(item.id, {...item, rName: [item.rName]})
    }
})
var arr1 = Array.from(map.values())
console.log(JSON.stringify(arr1))

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM