[英]using filter in a nested array of object
I want to have an array that return certain property base on the checked property. 我想有一个数组,它返回checked属性的某些属性。
const data = [
{
"param": "type",
"id": 6,
"data": [
{
"name": "Collect",
"filterKey": "collect",
"checked": false
},
{
"name": "Redeem",
"filterKey": "redeem",
"checked": true
}
]
},
{
"param": "country",
"id": 5,
"data": [
{
"name": "Malaysia",
"filterKey": "my",
"checked": true
},
{
"name": "Singapore",
"filterKey": "sg",
"checked": false
}
]
}
]
Why my code below doesn't work? 为什么我的代码不起作用? It's a function I use for my check or uncheck event 这是我用于检查或取消选中事件的功能
const checkedKeys = data.map(o => {
return o.data.filter(o2 => {
return o2.checked === true
}).filterKey
})
I expect to get ['my', 'redeem']
for above case. 对于上述情况['my', 'redeem']
我希望得到['my', 'redeem']
。
Why my code below doesn't work? 为什么我的代码不起作用? It's a function I use for my check or uncheck event 这是我用于检查或取消选中事件的功能
Because filter
returns an array and that array won't have filterKey
property. 因为filter
返回一个数组 ,该数组不具有filterKey
属性。
Use reduce
, filter
and map
使用reduce
, filter
和map
var output = data.reduce( ( a, b ) => //use reduce to accumulate all filtered values
a.concat( b.data.filter( o2 => //filter by checked
o2.checked ).map( o3 => // map to get only the filterKey property
o3.filterKey ) ) , []); //[] is the initial value of accumulator
Demo 演示
var data = [ { "param": "type", "id": 6, "data": [ { "name": "Collect", "filterKey": "collect", "checked": false }, { "name": "Redeem", "filterKey": "redeem", "checked": true } ] }, { "param": "country", "id": 5, "data": [ { "name": "Malaysia", "filterKey": "my", "checked": true }, { "name": "Singapore", "filterKey": "sg", "checked": false } ] } ]; var output = data.reduce( (a,b) => a.concat( b.data.filter( o2 => o2.checked ).map( o3 => o3.filterKey ) ) , []) ; console.log( output );
You can try something like this as well. 你也可以试试这样的东西。
acc
in below example ). ( acc
在下面例子 )。 data
and in turn loop over data[i].data
循环data
,然后循环data[i].data
checked
is true, push filterKey
value to acc
. 检查checked
是否为true,将filterKey
值推filterKey
acc
。 ES5 Version: ES5版本:
var data = [ { "param": "type", "id": 6, "data": [ { "name": "Collect", "filterKey": "collect", "checked": false }, { "name": "Redeem", "filterKey": "redeem", "checked": true } ] }, { "param": "country", "id": 5, "data": [ { "name": "Malaysia", "filterKey": "my", "checked": true }, { "name": "Singapore", "filterKey": "sg", "checked": false } ] } ]; var result = data.reduce(function(acc, obj) { obj.data.forEach(function(curObj) { if (curObj.checked) { acc.push(curObj.filterKey) } }) return acc; }, []) console.log(result);
ES6 Version: ES6版本:
var data = [ { "param": "type", "id": 6, "data": [ { "name": "Collect", "filterKey": "collect", "checked": false }, { "name": "Redeem", "filterKey": "redeem", "checked": true } ] }, { "param": "country", "id": 5, "data": [ { "name": "Malaysia", "filterKey": "my", "checked": true }, { "name": "Singapore", "filterKey": "sg", "checked": false } ] } ]; var result = data.reduce((acc, obj) => { obj.data.forEach(({filterKey, checked}) => { checked && acc.push(filterKey) }) return acc; }, []) console.log(result);
You can achieve this by using simple javascript too which is seemingly easy to understand and will you to edit easily for future changes. 您可以通过使用简单的javascript来实现这一点,这看起来很容易理解,并且您可以轻松编辑以备将来的更改。 Although the complexity based on time and space is same when you use ECMA script or pure javascript. 虽然使用ECMA脚本或纯JavaScript时基于时间和空间的复杂性相同。 Just depends on shorthand codes. 只取决于速记码。
var data = [ { "param": "type", "id": 6, "data": [ { "name": "Collect", "filterKey": "collect", "checked": false }, { "name": "Redeem", "filterKey": "redeem", "checked": true } ] }, { "param": "country", "id": 5, "data": [ { "name": "Malaysia", "filterKey": "my", "checked": true }, { "name": "Singapore", "filterKey": "sg", "checked": false } ] } ]; var checkedKeys = []; data.forEach((dataItem)=>{ dataItem.data.forEach((innerData)=>{ if(innerData.checked){ checkedKeys.push(innerData.filterKey); } }); }); console.log(checkedKeys)
A solution with array.protoype.concat , array.protoype.filter , array.protoype.map and spread operator of ES6: 使用array.protoype.concat , array.protoype.filter , array.protoype.map和ES6的spread运算符的解决方案:
var data = [ { "param": "type", "id": 6, "data": [{"name": "Collect", "filterKey": "collect", "checked": false }, {"name": "Redeem", "filterKey": "redeem", "checked": true }]}, {"param": "country","id": 5,"data": [{"name": "Malaysia","filterKey": "my","checked": true}, {"name": "Singapore","filterKey": "sg","checked": false}]}]; var result = [].concat(...data.map(o => o.data)).filter(d => d.checked).map(d => d.filterKey); console.log(result);
data.map( // iterate over the top level list
x => (
x.data.filter( // select only the checked items from the nested `data` list
y => y.checked
).map( // select only the `filterKey` property of the filtered items
y => y.filterKey
)
)
).reduce( // flatten the end-result [['redeem'],['my']] -> ['redeem', 'my]
(acc, prev) => acc.concat(prev), []
);
Cleaner way to achieve same thing. 更清洁的方式来实现同样的事情。
data.map(o => o.data) //gets dataArray .reduce((a, c) => a.concat(c), []) //concats array .filter(o => o.checked) // filters for checked= true .map(o => o.filterKey) //returns filter key
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.