拉属性对象作为父对象

问题描述:

我有这样一组数据,我没有控制(其托管API的地方,我都进不去)拉属性对象作为父对象

let x = [ 
    {name: "james", age: 10, school: {id:1, name:"London"}}, 
    {name: "james_2", age: 11, school: {id:1, name:"London"}}, 
    {name: "john", age: 12, school: {id:2, name:"India"}}, 
    {name: "johnny", age: 56, school: {id:3, name:"USA"}} 
] 

我怎能组全校第一?我需要的格式是这样

[{ 
    id:1, 
    name: "London", 
    data: [{ 
     name: "james", age: 10, school: {id:1, name:"London" 
    },{name: "james_2", age: 11, school: {id:1, name:"London"}}] 
}] 

您可以使用_.groupBy()并将结果返回映射到数组:

const data = [{"name":"james","age":10,"school":{"id":1,"name":"London"}},{"name":"james_2","age":11,"school":{"id":1,"name":"London"}},{"name":"john","age":12,"school":{"id":2,"name":"India"}},{"name":"johnny","age":56,"school":{"id":3,"name":"USA"}}]; 
 

 
const result = _(data) 
 
    .groupBy('school.name') 
 
    .map((group) => ({ // or Object.assign({}, group[0].school, { data: group }); 
 
    ...group[0].school, 
 
    data: group 
 
    })) 
 
    .value(); 
 

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

您可以通过组合使用Array#reduceMap离不开lodash同样的事情:

const data = [{"name":"james","age":10,"school":{"id":1,"name":"London"}},{"name":"james_2","age":11,"school":{"id":1,"name":"London"}},{"name":"john","age":12,"school":{"id":2,"name":"India"}},{"name":"johnny","age":56,"school":{"id":3,"name":"USA"}}]; 
 

 
const result = [...data.reduce((map, item) => { 
 
    const school = map.get(item.school.name) || { // or Object.assign({}, { item.school }, { data: [] }) 
 
    ...item.school, data: [] 
 
    }; 
 
    
 
    school.data.push(item); 
 
    
 
    map.set(item.school.name, school); 
 
    
 
    return map; 
 
}, new Map()).values()] 
 

 
console.log(result);

+0

什么是这个? _(数据) –

+0

组[0] .school为什么在这里使用[0]? –

+0

_(数据)启动一个lodash链。 group [0] .school用于从组的第一个元素中获取学校名称和ID。 –

您可以创建一个在其ID存储每个学校一个哈希对象,所以你可以把学生吧:

var hash=x.reduce(function(obj,el){ 
(obj[el.school.id]=obj[el.school.id]||{id:el.school.id,name:el.school.name,data:[]}).data.push({name:el.name,age:el.age}); 
    return obj; 
},{}); 

var arr=Object.values(hash); 

http://jsbin.com/vedajijiye/edit?console

您可以使用reduce()方法:

let data = [ 
 
    {name: "james", age: 10, school: {id:1, name:"London"}}, 
 
    {name: "james_2", age: 11, school: {id:1, name:"London"}}, 
 
    {name: "john", age: 12, school: {id:2, name:"India"}}, 
 
    {name: "johnny", age: 56, school: {id:3, name:"USA"}} 
 
]; 
 
let schools = data.reduce((acc, x) => { 
 
    // Check if the school already exists 
 
    let school = acc.find(y => y.id === x.school.id); 
 
    if (!school) { 
 
    // If not, the current school is the school of the current person 
 
    school = x.school; 
 
    school.data = []; 
 
    acc.push(school); 
 
    } else { 
 
    // Prevent duplication of school objects with the same id 
 
    x.school = school; 
 
    } 
 
    school.data.push(x); 
 
    return acc; 
 
}, []); 
 
console.log(schools);

可以使用lodash库GROUPBY

let x = [ 
    {name: "james", age: 10, school: {id:1, name:"London"}}, 
    {name: "james_2", age: 11, school: {id:1, name:"London"}}, 
    {name: "john", age: 12, school: {id:2, name:"India"}}, 
    {name: "johnny", age: 56, school: {id:3, name:"USA"}} 
] 


var result2 = _.chain(x) 
    .groupBy(function(o){return o.school.name}) 
    .pairs() 
    .map(function (currentItem) { 
     return _.object(_.zip(["school", "name"], currentItem)); 
    }) 
    .value(); 
console.log(result2); 

检查此的jsfiddle: - http://jsfiddle.net/6yasy30a/

+0

pairs?那个有什么用? –

+0

@AlanJenshen _pairs(): - 创建对象的键值对的二维数组,例如: [[key1,value1],[key2,value2]]。 _.pairs({'barney':36,'fred':40}); // => [['barney',36],['fred',40]](迭代顺序不能保证) –

+0

你的逻辑比Ori的代码更复杂 –

let x = [ 
 
    {name: "james", age: 10, school: {id:1, name:"London"}}, 
 
    {name: "james_2", age: 11, school: {id:1, name:"London"}}, 
 
    {name: "john", age: 12, school: {id:2, name:"India"}}, 
 
    {name: "johnny", age: 56, school: {id:3, name:"USA"}} 
 
]; 
 

 
let result = []; 
 
for(var i = 0; i < x.length; i++) { 
 
    var person = x[i]; 
 
    var school = result.find(s => s.id === person.school.id); 
 
    if(!school) { 
 
    school = { 
 
     id: person.school.id, 
 
     name: person.school.name, 
 
     data: [] 
 
    }; 
 
    result.push(school); 
 
    } 
 
    school.data.push(person); 
 
} 
 

 
console.log(result);

使用减少,简单地推向一个新的对象进入你的结果数组,如果id不存在,否则只需更新t他在找到的对象中的数据数组

const myArray = x.reduce((res, data) => { 
    const found = res.find(o => o.id === data.school.id); 

    if (!found) { 
    res.push({ 
     id: data.school.id, 
     name: data.school.name, 
     data: [data] 
    }); 
    } else { 
    found.data.push(data); 
    } 
    return res; 
}, []); 


console.log(myArray)