[英]Filtering a nested array with objects by checking another nested array with object - JavaScript
[英]Filtering array of objects by searching nested object properties
我有一个对象数组,我想通过比较嵌套属性和搜索词来过滤。
例如:
var array = [
{category: 'Business'
users: [
{name: 'Sally'
tags: [{tag: 'accounting'}, {tag: 'marketing'},...]
},
{name: 'Bob'
tags: [{tag: 'sales'}, {tag: 'accounting'},...]
}...
]
},
{category: 'Heritage'
users: [
{name: 'Linda'
tags: [{tag: 'Italy'}, {tag: 'Macedonia'},...]
},
{name: 'George'
tags: [{tag: 'South Africa'}, {tag: 'Chile'},...]
},...
]
},...
[
基本上我想通过搜索项过滤对象的基础数组,搜索项包括嵌套对象2数组中的标记属性字符串中的字符。
因此,搜索“市场”将导致
[
{category: 'Business'
users: [
{name: 'Sally'
tags: [{tag: 'accounting'}, {tag: 'marketing'},...]
},
{name: 'Bob'
tags: [{tag: 'sales'}, {tag: 'accounting'},...]
}...
]
}
]
谢谢。
您可以使用Array#filter
通过使用Array#some
查看嵌套数组。
如果在嵌套数组中找到标记,则迭代停止并将结果返回给过滤器回调。
var array = [{ category: 'Business', users: [{ name: 'Sally', tags: [{ tag: 'accounting' }, { tag: 'marketing' }] }, { name: 'Bob', tags: [{ tag: 'sales' }, { tag: 'accounting' }] }] }, { category: 'Heritage', users: [{ name: 'Linda', tags: [{ tag: 'Italy' }, { tag: 'Macedonia' }] }, { name: 'George', tags: [{ tag: 'South Africa' }, { tag: 'Chile' }] }] }], tag = 'marketing', result = array.filter(a => a.users.some(u => u.tags.some(t => t.tag.includes(tag)))); console.log(result);
.as-console-wrapper { max-height: 100% !important; top: 0; }
尝试这个:
function search(term){
return
Array.filter(array,function(item){
return JSON.stringify(obj).indexOf(term)!=-1;
});
}
所以:
console.log(search('market'));
我希望对你有所帮助:)
使用Array.prototype.some()
函数的解决方案:
var arr = [{ category: 'Business', users: [{ name: 'Sally', tags: [{ tag: 'accounting' }, { tag: 'marketing' }] }, { name: 'Bob', tags: [{ tag: 'sales' }, { tag: 'accounting' }] }] }, { category: 'Heritage', users: [{ name: 'Linda', tags: [{ tag: 'Italy' }, { tag: 'Macedonia' }] }, { name: 'George', tags: [{ tag: 'South Africa' }, { tag: 'Chile' }] }] }], search_key = 'market', result = []; arr.forEach(function(o){ if (o.users.some(function(v){ return v.tags.some(function(i){ return i.tag.indexOf(search_key) !== -1; }); })) { result.push(o); } }); console.log(result);
concatAll
和concatMap
定义取自http://reactivex.io/learnrx/
Array.prototype.concatAll = function() {
var results = [];
this.forEach(function(subArray) {
results.push.apply(results, subArray);
});
return results;
};
Array.prototype.concatMap = function(projectionFunctionThatReturnsArray) {
return this.
map(function(item) {
return projectionFunctionThatReturnsArray(item);
}).
// apply the concatAll function to flatten the two-dimensional array
concatAll();
};
function filterByTags(keyword) {
return array.filter(function (item) {
var allTags = item.users.concatMap(function (user) {
return user.tags.map(function (tag) {
return tag.tag;
});
});
return allTags.some(function (tag) {
return tag.indexOf(keyword) > -1;
});
});
}
console.log(filterByTags('market'));
当然,您可以内联allTags
变量以获得更简洁。
应用于初始数组的filter
将返回所有具有标记包含所提供关键字的用户的项目。 策略是构建用户标签的扁平版本并在其上应用some
。
您可以像这样使用array.filter
:
function getFiltered(val) {
return array.filter(category == val);
}
此函数将返回一个新的数组实例,仅使用作为val
参数传递的category
键。
注意:我采用类似快捷方式的方法,主要是为问题提供不同的视角。
您可以创建users
属性的json字符串并在其中进行搜索,而不是深入搜索主array
下的属性和数组。 所以我创建了一个新属性usersString
,它临时存储了针对users
属性的值的JSON字符串。
item.usersString = JSON.stringify(item.users);
现在,这不是一个完美的实现,但它几乎总是有效。 此外,如果您将此属性存储在浏览器中(不将其存储回数据库),并在每次用户搜索时使用它来快速搜索,我认为深度搜索整个数组会更有效。
var array = [{ category: 'Business', users: [{ name: 'Sally', tags: [{ tag: 'accounting' }, { tag: 'marketing' }] }, { name: 'Bob', tags: [{ tag: 'sales' }, { tag: 'accounting' }] } ] }, { category: 'Heritage', users: [{ name: 'Linda', tags: [{ tag: 'Italy' }, { tag: 'Macedonia' }] }, { name: 'George', tags: [{ tag: 'South Africa' }, { tag: 'Chile' }] } ] } ]; var key = "market"; // Convert the users property into a string - so that it works as a quick search target. array.forEach(function(item) { item.usersString = JSON.stringify(item.users); }); var filteredItems = array.filter(function(item) { return item.usersString.toLowerCase().indexOf(key.toLowerCase()) >= 0; }); // Delete the usersString property - if required. filteredItems.forEach(function(item) { item.usersString = undefined; // Or, // delete item.usersString; }) console.log(filteredItems);
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.