简体   繁体   English

如何过滤子对象的属性并返回带有在Javascript中传递过滤器的子对象的父对象?

[英]How to filter on properties of children object and return the parent with children that passes the filter in Javascript?

I want to filter on the property of children object and return parents with children that passes the filter. 我想过滤子对象的属性并返回带有通过过滤器的子对象的父对象。

I tried with combination of Array.filter, Array.some, and Object.values, but I can't think of a way to get the key back once Ive used Object.values 我尝试使用Array.filter,Array.some和Object.values的组合,但是一旦我使用了Object.values,我想不出一种方法来获取密钥。

var data = {
    parent1: {
        child1: {
            source: true
        },
        child2: {
            source: true
        }
    },
    parent2: {
        child3: {
            source: true
        },
        child4: {
            source: false
        }
    },
    parent3: {
        child5: {
                source: false
        }
    }
}

I want the outcome to be: 我希望结果如下:

var afterFilter = {
    parent1: {
        child1: {
            source: true
        },
        child2: {
            source: true
        }
    },
    parent2: {
        child3: {
            source: true
        }
    }
}

Try this using Array.reduce and Object.entries , for each parent entry iterate through the children of the parent object filter it based on the source . 尝试使用Array.reduceObject.entries ,为每个父条目迭代通过父对象的子对象基于source对其进行过滤。

If the current child of the parent has the source as true then add it to the accumulator acc of the reduce else ignore it: 如果父节点的当前子节点的源为true则将其添加到reduce的累加器acc中,否则忽略它:

 const data = {parent1:{child1:{source:true},child2:{source:true}},parent2:{child3:{source:true},child4:{source:false}},parent3:{child5:{source:false}}}; const res = Object.entries(data).reduce((acc, [key, value]) =>{ for(child in value){ //value is the child-object of the parent, iterating throgh all the key of the child and checking if the source is true for this key of the child if(value[child].source){ acc[key] = {...acc[key], [child] : value[child]}; //using spread operator to preserve previous values } } return acc; }, {}); console.log(res); 

Instead of using Array methods, you can also try a simple for...of loop: 您也可以尝试一个简单的for...of循环来代替使用Array方法:

 var data = { parent1: { child1: { source: true }, child2: { source: true } }, parent2: { child3: { source: true }, child4: { source: false } }, parent3: { child5: { source: false } } } var afterFilter = {}; for (const [key, value] of Object.entries(data)){ for (const [k, v] of Object.entries(value)){ const { source } = v; if (source !== true) continue; // If `afterFilter[key]` does not exist, init with {} afterFilter[key] = afterFilter[key] || {}; afterFilter[key][k] = { source }; } } console.log(afterFilter) 

If you find to find whose children is true and return that parent, maybe this is correct answer for you 如果你发现谁的孩子是真的并且回归那个父母,也许这对你来说是正确的答案

const data = [
{ name: 'parent1', parent : { child: { source : true } } },
{ name: 'parent2', parent : { child: { source : true } } },
{ name: 'parent3', parent : { child: { source : false } } }

]; ]。

const newData = data.filter((e)=> e.parent.child.source === true);
console.log(newData);

This is my solution. 这是我的解决方案。 Try this 尝试这个

 var data = { parent1: { child1: { source: true }, child2: { source: true } }, parent2: { child3: { source: true }, child4: { source: false } }, parent3: { child5: { source: false } } } var afterFilter = {} for(var key in data){ for(var childkey in data[key]){ if(data[key][childkey].source){ if(afterFilter[key]) afterFilter[key][childkey] = data[key][childkey] else afterFilter[key] = {[childkey]: data[key][childkey]} } } } console.log(afterFilter); 

If you want a solution with a reuseable function, I suggest looking at this implementation. 如果您想要一个具有可重用功能的解决方案,我建议您查看此实现。

 const data = {parent1:{child1:{source:true},child2:{source:true}},parent2:{child3:{source:true},child4:{source:false}},parent3:{child5:{source:false}}} function objectMapReduce (object, map, filter) { // iterate key-value pairs of object return Object.entries(object).reduce( (accumulator, [key, value]) => { // map each value in object const result = map(value, key, object) // filter each mapped value return filter(result, key, object) ? Object.assign(accumulator, { [key]: result }) : accumulator }, // initial value of accumulator {} ) } const afterFilter = objectMapReduce( data, // map-reduce each parent in data parent => objectMapReduce( parent, // map-reduce each child in parent ({ source}) => ({ source }), // copy each child ({ source }) => source // keep child if source is true ), parent => Object.keys(parent).length > 0 // keep non-empty parent ) console.log(afterFilter) 

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM