Encuentre valor en la matriz javascript de objetos profundamente nesteds con ES6

En una matriz de objetos necesito encontrar un value , donde key es activity : sin embargo, la key activity puede estar profundamente anidada en la matriz de esta manera:

 const activityItems = [ { name: 'Sunday', items: [ { name: 'Gym', activity: 'weights', }, ], }, { name: 'Monday', items: [ { name: 'Track', activity: 'race', }, { name: 'Work', activity: 'meeting', }, { name: 'Swim', items: [ { name: 'Beach', activity: 'scuba diving', }, { name: 'Pool', activity: 'back stroke', }, ], }, ], }, {} ... {} ... ]; 

Así que escribí un algoritmo recursivo para averiguar si una determinada actividad está en la matriz:

 let match = false; const findMatchRecursion = (activity, activityItems) => { for (let i = 0; i < activityItems.length; i += 1) { if (activityItems[i].activity === activity) { match = true; break; } if (activityItems[i].items) { findMatchRecursion(activity, activityItems[i].items); } } return match; }; 

¿Existe una forma ES6 de determinar si existe una actividad en una matriz como esta?

Probé algo como esto:

 const findMatch(activity, activityItems) { let obj = activityItems.find(o => o.items.activity === activity); return obj; } 

Pero esto no funcionará con actividades profundamente anidadas.

Gracias

Puede usar some() método y recursión para encontrar si existe actividad en cualquier nivel y devolver verdadero / falso como resultado.

 const activityItems = [{"name":"Sunday","items":[{"name":"Gym","activity":"weights"}]},{"name":"Monday","items":[{"name":"Track","activity":"race"},{"name":"Work","activity":"meeting"},{"name":"Swim","items":[{"name":"Beach","activity":"scuba diving"},{"name":"Pool","activity":"back stroke"}]}]}] let findDeep = function(data, activity) { return data.some(function(e) { if(e.activity == activity) return true; else if(e.items) return findDeep(e.items, activity) }) } console.log(findDeep(activityItems, 'scuba diving')) 

Aunque no es tan elegante como un algoritmo recursivo, podría JSON.stringify () la matriz, lo que da esto:

 [{"name":"Sunday","items":[{"name":"Gym","activity":"weights"}]},{"name":"Monday","items":[{"name":"Track","activity":"race"},{"name":"Work","activity":"meeting"},{"name":"Swim","items":[{"name":"Beach","activity":"scuba diving"},{"name":"Pool","activity":"back stroke"}]}]}] 

Luego puedes usar un literal de plantilla para buscar el patrón:

 `"activity":"${activity}"` 

Función completa:

 findMatch = (activity, activityItems) => JSON.stringify(activityItems).includes(`"activity":"${activity}"`); 
 const activityItems = [{ name: 'Sunday', items: [{ name: 'Gym', activity: 'weights', }, ], }, { name: 'Monday', items: [{ name: 'Track', activity: 'race', }, { name: 'Work', activity: 'meeting', }, { name: 'Swim', items: [{ name: 'Beach', activity: 'scuba diving', }, { name: 'Pool', activity: 'back stroke', }, ], }, ], } ]; findMatch = (activity, activityItems) => JSON.stringify(activityItems).includes(`"activity":"${activity}"`); console.log(findMatch('scuba diving', activityItems)); //true console.log(findMatch('dumpster diving', activityItems)); //false 

Primero, su función podría mejorarse deteniéndose una vez que se encuentre una coincidencia a través de la llamada recursiva. Además, ambos están declarando match afuera, así como devolviéndolo. Probablemente sea mejor simplemente volver.

 const findMatchRecursion = (activity, activityItems) => { for (let i = 0; i < activityItems.length; i += 1) { if (activityItems[i].activity === activity) { return true; } if (activityItems[i].items && findMatchRecursion(activity, activityItems[i].items) { return true; } } return false; }; 

No hay una búsqueda profunda integrada, pero puede usar .find con una función nombrada si lo desea.

 var result = !!activityItems.find(function fn(item) { return item.activity === "Gym" || (item.items && item.items.find(fn)); });