[英]Create array of objects by key from array of objects
這里有很多這樣的問題,但我找不到符合我需求的問題。 我正在尋找一個相對簡單的解決方案,關於如何根據鍵將數組中的對象堆疊到新數組中。
在示例數據中,我們通過“船”鍵對對象進行分組。
原始數據:
var myObjArray = [
{
name:'Malcolm Reynolds',
ship:'Serenity'
},
{
name: 'Carmen Ibanez',
ship: 'Rodger Young',
},
{
name: 'Zander Barcalow',
ship: 'Rodger Young',
},
{
name:'Hoban Washburne',
ship:'Serenity'
},
{
name:'James Kirk',
ship:'USS Enterprise'
}
];
重組數據:
var myNewObjArray = [
[{
name:'Malcolm Reynolds',
ship:'Serenity'
},
{
name:'Hoban Washburne',
ship:'Serenity'
}],
[{
name: 'Carmen Ibanez',
ship: 'Rodger Young',
},
{
name: 'Zander Barcalow',
ship: 'Rodger Young',
}],
{
name:'James Kirk', // optionally also stick in an array
ship:'USS Enterprise'
}
];
如果有人有解決方案,我會很感激,我目前的嘗試至少可以說是草率的。
您可以將對象和ship
值作為同一組的關鍵。 對於結果,只取對象的值。
var data = [{ name: 'Malcolm Reynolds', ship: 'Serenity' }, { name: 'Carmen Ibanez', ship: 'Rodger Young' }, { name: 'Zander Barcalow', ship: 'Rodger Young' }, { name: 'Hoban Washburne', ship: 'Serenity' }, { name: 'James Kirk', ship: 'USS Enterprise' }], grouped = Object.values(data.reduce((r, o) => { if (!r[o.ship]) { r[o.ship] = o; return r; } if (!Array.isArray(r[o.ship])) r[o.ship] = [r[o.ship]]; r[o.ship].push(o); return r; }, {})); console.log(grouped);
.as-console-wrapper { max-height: 100% !important; top: 0; }
一種使用Map
的方法
var data = [{ name: 'Malcolm Reynolds', ship: 'Serenity' }, { name: 'Carmen Ibanez', ship: 'Rodger Young' }, { name: 'Zander Barcalow', ship: 'Rodger Young' }, { name: 'Hoban Washburne', ship: 'Serenity' }, { name: 'James Kirk', ship: 'USS Enterprise' }], grouped = Array.from( data .reduce((m, o) => m.set(o.ship, [...(m.get(o.ship) || []), o]), new Map) .values(), a => a.length === 1 ? a[0] : a ); console.log(grouped);
.as-console-wrapper { max-height: 100% !important; top: 0; }
找到並重復刪除船舶名稱,然后找到每艘船的人員。
const myObjArray = [ { name:'Malcolm Reynolds', ship:'Serenity' }, { name: 'Carmen Ibanez', ship: 'Rodger Young', }, { name: 'Zander Barcalow', ship: 'Rodger Young', }, { name:'Hoban Washburne', ship:'Serenity' }, { name:'James Kirk', ship:'USS Enterprise' } ]; const ships = myObjArray.map(({ship}) => ship).filter((ship, i, arr) => arr.indexOf(ship) === i); const personnelArray = ships.map(ship => myObjArray.filter(entry => entry.ship === ship)); console.log(personnelArray);
另一個干凈而優雅的解決方案是與Lodash合作 。
首先,使用相關鍵對數組進行分組。然后,從對象中獲取值。
來自文檔:
創建一個對象,該對象由通過iteratee運行集合的每個元素的結果生成的鍵組成。 分組值的順序由它們在集合中出現的順序確定。 每個鍵的對應值是負責生成密鑰的元素數組。 使用一個參數調用iteratee :( value)。
const myObjArray = [ { name:'Malcolm Reynolds', ship:'Serenity' }, { name: 'Carmen Ibanez', ship: 'Rodger Young', }, { name: 'Zander Barcalow', ship: 'Rodger Young', }, { name:'Hoban Washburne', ship:'Serenity' }, { name:'James Kirk', ship:'USS Enterprise' } ]; var result =_.values((_.groupBy(myObjArray , 'ship'))); console.log(result);
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.16.4/lodash.min.js"></script>
可能不是最高效的,但這應該有效。
var tempObj = {};
myObjArray.forEach((item)=>{
var ship = item.ship;
if (!tempObj.hasOwnProperty(ship)) {
tempObj[ship] = []; //create the key in the key in the obj and init to an empty array
}
tempObj[ship].push(item); //add the item to the array
});
var myNewObjArray = [];
for (key in tempObj) {
myNewObjArray.push([]); //add a new array for each key in the tempObj
tempObj[key].forEach((item)=>{ //iterate over the array of items in the tempObj for that key
myNewObjArray[myNewObjArray.length-1].push(item); //add the item to the last array in the object which should have been created.
});
}
不確定你打算如何使用數據,但是更簡潔的數據結構看起來就像船上有員工的對象,而不是一個數組,其中船名以冗余的方式不斷重復? 這個數據結構怎么樣?
var myObjArray = [ { name:'Malcolm Reynolds', ship:'Serenity' }, { name: 'Carmen Ibanez', ship: 'Rodger Young', }, { name: 'Zander Barcalow', ship: 'Rodger Young', }, { name:'Hoban Washburne', ship:'Serenity' }, { name:'James Kirk', ship:'USS Enterprise' } ]; const staffShips = data => data.reduce((ships, item) => { const ship = ships[item.ship]; if (ship) { ship.push(item.name); } else { ships[item.ship] = [ item.name ]; } return ships; }, {}); console.log(staffShips(myObjArray));
這略有不同,因為它是一個帶鍵的對象,但這些鍵包含數組,其中包含您希望如何看到它的數據。
var newObject = {};
for (var i in myObjArray) {
var newKey = myObjArray[i].ship.replace(/\s+/g, '');
if (typeof(newObject[newKey]) == "undefined") newObject[newKey] = [];
newObject[newKey].push({
name: myObjArray[i].name, ship: myObjArray[i].ship
});
}
這里有另一種方法,首先,我們使用Array.reduce()生成一個對象,該對象將按ship屬性對元素進行分組。 然后我們在生成的Object.values()上使用Array.map()來刪除數組(如果只保存一個元素)。 如果您真的不需要最后一步,那么地圖可以是可選的。
var myObjArray = [ {name:'Malcolm Reynolds', ship:'Serenity'}, {name: 'Carmen Ibanez', ship: 'Rodger Young'}, {name: 'Zander Barcalow', ship: 'Rodger Young'}, {name:'Hoban Washburne', ship:'Serenity'}, {name:'James Kirk', ship:'USS Enterprise'} ]; let res = myObjArray.reduce((acc, obj) => { acc[obj.ship] = acc[obj.ship] || []; acc[obj.ship].push(obj); return acc; }, {}); res = Object.values(res).map(arr => (arr.length <= 1 ? arr[0] : arr)); console.log(res);
.as-console {background-color:black !important; color:lime;} .as-console-wrapper {max-height:100% !important; top:0;}
在Javascript中,要按屬性對對象進行分組,可以使用Array.prototype.reduce()方法將輸入數組數據合並為一組結果,按鍵分組(在本例中為“ship”)。 使用Object.values通過刪除鍵從結果集中提取值
var data = [ { name: 'Malcolm Reynolds', ship: 'Serenity' }, { name: 'Carmen Ibanez', ship: 'Rodger Young' }, { name: 'Zander Barcalow', ship: 'Rodger Young' }, { name: 'Hoban Washburne', ship: 'Serenity' }, { name: 'James Kirk', ship: 'USS Enterprise' }]; var myNewObjArray = data.reduce((res,obj) =>{ const key = obj.ship; if(!res[key]){ res[key] = []; } res[key].push(obj) return res; }, {}); console.log(Object.values(myNewObjArray));
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.