如何按 javascript 中的类别对数据数组进行分组
How to grouping array of data by its category in javascript
这是我的数据:
pets: [{id: 1, name: Susi, species: dog, gender: female},{id: 2, name: Xixi, species: dog, gender: female},{id: 3, name: Boss, species: rabbit, gender: male},{id: 4, name: Bunny, species: rabbit, gender: male},{id: 5, name: kitty, species: cat, gender: female},{id: 6, name: Garfield, species: cat, gender: male}]
我如何将这些数据转换为按照宠物的种类和性别对每只宠物进行分组,如下所示:
data: [{species: dog, genders: [{gender: male, pets: [{id: 1, name: Susi, species: dog, gender: female},]}, {gender: female, pets: [{id: 2, name: Xixi, species: dog, gender: female},]}, ]},{species: cat, genders: [{gender: male, pets: [{id: 6, name: Garfield, species: cat, gender: male}]},{gender: female, pets: [{id:5, name: kitty, species: cat, gender: female},]},]},{species: rabbit,genders: [{gender: male, pets: [{id: 3, name: Boss, species: rabbit, gender: male},{id: 4, name: Bunny, species: rabbit, gender: male},]},{gender: female, pets: []},]}]
我的代码是:
const species = pets.reduce((acc, curr) => {
let item = acc.find(
(item) =>
item.spesies === curr.species || item.gender === curr.gender
);
if (item) {
item.genders.push({
gender: curr.gender,
pets: [
{
id: acc.id,
name: curr.name
}
]
});
} else {
acc.push({
species: curr.species
genders: [
gender: curr.gender,
pets: [
{
id: acc.id,
name: curr.name
}
]
]
});
}
return acc;}, []);
我的代码的结果是:
data: [{species: dog, genders: [{gender: female, pets: Array(1)},{gender: female, pets: Array(1)},]},species: cat, genders: [{gender: male, pets: Array(1)},{gender: female, pets: Array(1)},]},{species: rabbit, genders: [{gender: male, pets: Array(1)},{gender: male, pets: Array(1)}]}]
我希望最终结果像上面的第二个数组一样。
有谁知道如何更好地做到这一点并解释我所缺少的东西。谢谢!!
你可以这样做
const pets = [
{id: 1, name: 'Susi', species: 'dog', gender: 'female'},
{id: 2, name: 'Xixi', species: 'dog', gender: 'female'},
{id: 3, name: 'Boss', species: 'rabbit', gender: 'male'}, {id: 4, name: 'Bunny', species: 'rabbit', gender: 'male'}, {id: 5, name: 'kitty', species: 'cat', gender: 'female'},
{id: 6, name: 'Garfield', species: 'cat', gender: 'male'}
]
const data = Object.values(pets.reduce((res, pet) => {
const existingSpecies = res[pet.species] || {species: pet.species, genders:{}}
const existingGender = existingSpecies.genders[pet.gender] || {gender: pet.gender, pets:[]}
return {
...res,
[pet.species]: {
...existingSpecies,
genders: {
...existingSpecies.genders,
[pet.gender]: {
...existingGender,
pets: [...existingGender.pets, pet]
}
}
}
}
}, {})).map(s => ({...s, genders: Object.values(s.genders)}))
console.log (data)
我认为用图像可视化问题更清楚,但是没关系...
反正我写了下面这个函数应该是最容易理解的了
const pets = [
{id: 1, name: 'Susi' , species: 'dog', gender: 'female'},
{id: 2, name: 'Mini' , species: 'dog', gender: 'female'},
{id: 3, name: 'Jojo' , species: 'cat', gender: 'male'},
{id: 4, name: 'Band' , species: 'cat', gender: 'male'},
{id: 5, name: 'Tommy' , species: 'rabbit', gender: 'male'}
]
function createNewData(pets){
// newList that we will be constructing
const newData = []
//Search in dictionary and get all de Unique Species types
const speciesList = pets
.map(({ species }) => species)
.filter((v, i, a) => a.indexOf(v) === i)
//For each unique species that we found in pets
for(let i = 0; i < speciesList.length; i++){
//Inside this loop we will construct each specie object
const specie = speciesList[i]
const newSpeciesObj = {species: specie, genders: [] }
//The male list will be inside the maleGenderObj
const maleList = []
//The female list will be inside the femaleGenderObj
const femaleList = []
for(let i = 0; i < pets.length; i++){
//Inside this loop we add items to the maleList and femaleList,
//if they are of the current specie
if(pets[i].species == specie) {
if (pets[i].gender == 'male'){
maleList.push(pets[i])
} else {
femaleList.push(pets[i])
}
}
}
//Here we push the maleGenderObject into genders list
newSpeciesObj.genders.push({gender: 'male', pets: maleList})
//Here we push the femaleGenderObject into genders list
newSpeciesObj.genders.push({gender: 'female', pets: femaleList})
//We do this for all the species we found at the original data
newData.push(newSpeciesObj)
}
return newData
}
console.log(createNewData(pets))
我目前正在审查您的代码以尝试使其正常工作!
这是我的数据:
pets: [{id: 1, name: Susi, species: dog, gender: female},{id: 2, name: Xixi, species: dog, gender: female},{id: 3, name: Boss, species: rabbit, gender: male},{id: 4, name: Bunny, species: rabbit, gender: male},{id: 5, name: kitty, species: cat, gender: female},{id: 6, name: Garfield, species: cat, gender: male}]
我如何将这些数据转换为按照宠物的种类和性别对每只宠物进行分组,如下所示:
data: [{species: dog, genders: [{gender: male, pets: [{id: 1, name: Susi, species: dog, gender: female},]}, {gender: female, pets: [{id: 2, name: Xixi, species: dog, gender: female},]}, ]},{species: cat, genders: [{gender: male, pets: [{id: 6, name: Garfield, species: cat, gender: male}]},{gender: female, pets: [{id:5, name: kitty, species: cat, gender: female},]},]},{species: rabbit,genders: [{gender: male, pets: [{id: 3, name: Boss, species: rabbit, gender: male},{id: 4, name: Bunny, species: rabbit, gender: male},]},{gender: female, pets: []},]}]
我的代码是:
const species = pets.reduce((acc, curr) => {
let item = acc.find(
(item) =>
item.spesies === curr.species || item.gender === curr.gender
);
if (item) {
item.genders.push({
gender: curr.gender,
pets: [
{
id: acc.id,
name: curr.name
}
]
});
} else {
acc.push({
species: curr.species
genders: [
gender: curr.gender,
pets: [
{
id: acc.id,
name: curr.name
}
]
]
});
}
return acc;}, []);
我的代码的结果是:
data: [{species: dog, genders: [{gender: female, pets: Array(1)},{gender: female, pets: Array(1)},]},species: cat, genders: [{gender: male, pets: Array(1)},{gender: female, pets: Array(1)},]},{species: rabbit, genders: [{gender: male, pets: Array(1)},{gender: male, pets: Array(1)}]}]
我希望最终结果像上面的第二个数组一样。 有谁知道如何更好地做到这一点并解释我所缺少的东西。谢谢!!
你可以这样做
const pets = [
{id: 1, name: 'Susi', species: 'dog', gender: 'female'},
{id: 2, name: 'Xixi', species: 'dog', gender: 'female'},
{id: 3, name: 'Boss', species: 'rabbit', gender: 'male'}, {id: 4, name: 'Bunny', species: 'rabbit', gender: 'male'}, {id: 5, name: 'kitty', species: 'cat', gender: 'female'},
{id: 6, name: 'Garfield', species: 'cat', gender: 'male'}
]
const data = Object.values(pets.reduce((res, pet) => {
const existingSpecies = res[pet.species] || {species: pet.species, genders:{}}
const existingGender = existingSpecies.genders[pet.gender] || {gender: pet.gender, pets:[]}
return {
...res,
[pet.species]: {
...existingSpecies,
genders: {
...existingSpecies.genders,
[pet.gender]: {
...existingGender,
pets: [...existingGender.pets, pet]
}
}
}
}
}, {})).map(s => ({...s, genders: Object.values(s.genders)}))
console.log (data)
我认为用图像可视化问题更清楚,但是没关系...
反正我写了下面这个函数应该是最容易理解的了
const pets = [
{id: 1, name: 'Susi' , species: 'dog', gender: 'female'},
{id: 2, name: 'Mini' , species: 'dog', gender: 'female'},
{id: 3, name: 'Jojo' , species: 'cat', gender: 'male'},
{id: 4, name: 'Band' , species: 'cat', gender: 'male'},
{id: 5, name: 'Tommy' , species: 'rabbit', gender: 'male'}
]
function createNewData(pets){
// newList that we will be constructing
const newData = []
//Search in dictionary and get all de Unique Species types
const speciesList = pets
.map(({ species }) => species)
.filter((v, i, a) => a.indexOf(v) === i)
//For each unique species that we found in pets
for(let i = 0; i < speciesList.length; i++){
//Inside this loop we will construct each specie object
const specie = speciesList[i]
const newSpeciesObj = {species: specie, genders: [] }
//The male list will be inside the maleGenderObj
const maleList = []
//The female list will be inside the femaleGenderObj
const femaleList = []
for(let i = 0; i < pets.length; i++){
//Inside this loop we add items to the maleList and femaleList,
//if they are of the current specie
if(pets[i].species == specie) {
if (pets[i].gender == 'male'){
maleList.push(pets[i])
} else {
femaleList.push(pets[i])
}
}
}
//Here we push the maleGenderObject into genders list
newSpeciesObj.genders.push({gender: 'male', pets: maleList})
//Here we push the femaleGenderObject into genders list
newSpeciesObj.genders.push({gender: 'female', pets: femaleList})
//We do this for all the species we found at the original data
newData.push(newSpeciesObj)
}
return newData
}
console.log(createNewData(pets))
我目前正在审查您的代码以尝试使其正常工作!