javaScript filter nested objects and arrays
15,098
Solution 1
Here nested some is used to check whether any of dish_has_categories
has CategoryId
equal to '8'
, if it is true
then we include that menu in final output else we don't
const data =[{ menuName: "Hot dogs", menu: [ { dishId: '1', dish_has_categories: [{ CategoryId: '8' }] }, { dishId: '2', dish_has_categories: [{ CategoryId: '9' }] }] }, { menuName: "Burgers", menu: [{ dishId: '3', dish_has_categories: [{ CategoryId: '6' }] }, { dishId: '4', dish_has_categories: [{ CategoryId: '4' }] }] }, { name: "Drinks", menu: [] } ]
let op = data.filter(val => {
let menu = val.menu.some(({dish_has_categories}) => dish_has_categories.some(({CategoryId}) => CategoryId === '8'))
return menu
})
console.log('filtered values -->\n',op)
let names = op.map(({menuName})=> menuName)
console.log('Names --> \n', names)
Solution 2
You can use filter()
with nested some()
.
The
some()
method tests whether at least one element in the array passes the test implemented by the provided function. It returns a Boolean value
const data = [{ menuName: "Hot dogs", menu: [ { dishId: '1', dish_has_categories: [{ CategoryId: '8' }] }, { dishId: '2', dish_has_categories: [{ CategoryId: '9' }] }] }, { menuName: "Burgers", menu: [{ dishId: '3', dish_has_categories: [{ CategoryId: '6' }] }, { dishId: '4', dish_has_categories: [{ CategoryId: '4' }] }] }, { name: "Drinks", menu: [] } ]
const res = data.filter(x =>
x.menu.some(y =>
y.dish_has_categories.some(z => z.CategoryId === '8')
)
);
console.log(res)
Related videos on Youtube
Author by
margherita pizza
Hello World, I'm Pathum kalhan. Senior full stack JavaScript developer based on Sri lanka.
Updated on September 15, 2022Comments
-
margherita pizza over 1 year
My use case is something like this.
- I have an array that has an object.
- That each object has an array called
menu
- Again that menu array has objected.
- That each object has an array
dish_has_categories
- In
dish_has_categories
array, if there is an object with CategoryId is equal to8
I want to filter out that root object.
My original data object
const data = [{ menuName: "Hot dogs", menu: [ { dishId: '1', dish_has_categories: [{ CategoryId: '8' }] }, { dishId: '2', dish_has_categories: [{ CategoryId: '9' }] }] }, { menuName: "Burgers", menu: [{ dishId: '3', dish_has_categories: [{ CategoryId: '6' }] }, { dishId: '4', dish_has_categories: [{ CategoryId: '4' }] }] }, { name: "Drinks", menu: [] } ]
My expect result is
[{ menuName: "Hot dogs", menu: [ { dishId: '1', dish_has_categories: [{ CategoryId: '8' }] }, { dishId: '2', dish_has_categories: [{ CategoryId: '9' }] }] }]
what I've done up to now is
const data2 = data.filter(element => { return element.menu.length > 0 })
I have no idea how to deep filter inside nested objects and arrays. Hope my question is clear to you all.
-
margherita pizza almost 5 yearsThanks a lot. This works! If I want to push this menu name ("Hot dogs") to new separate array. Where do I can do that?
-
Syed mohamed aladeen almost 5 yearsHi, can you please explain, why you are using
z.CategoryId === '8'
? 8 is hardcoded here. -
margherita pizza almost 5 yearsThanks a lot. This works! If I want to push this menu name ("Hot dogs") to new separate array. Where do I can do that?
-
Code Maniac almost 5 years@PathumSamararathna you want to get names of filtered values or all the values ? you can simply use map and return name only from map
-
Code Maniac almost 5 years@PathumSamararathna i have added example of getting names in new array too you can check :) always happy to help :)
-
Maheer Ali almost 5 years@PathumSamararathna You can use
map()
for that I have updated. -
Maheer Ali almost 5 years@SyedMohamedAladeen Becasue OP asked )"In dish_has_categories array, if there is an object with CategoryId is equal to 8 I want to filter out that root object."_