[英]Filter List of Object-Nested Objects with Object Containing Key-Array Pair
我试图想出一个最具描述性的标题。
我想出了一个解决方案,但它的效率非常低,因为它的顺序是 O(n^4) 左右,这很可悲。
我正在尝试根据过滤器对象和匹配的键值过滤并返回对象列表。
我将有一个电影列表movieList
,并且我将返回满足包含在movieFilter
object 中的所有键值对的所有电影。 在genre
的情况下,电影必须是流派之一。 由于销售额不在过滤器中,因此我们不会根据它进行过滤。
let movieFilter = {
"genre": ["Action", "Romance"],
"director": "Bob",
"writer": ["Jim", "Dave", "Alice"],
"duration": "2"
}
let movie = {
"genre" : "Action",
"people": {
"director": "Bob",
"writer": "Alice"
}
"boxoffice": "9,000,000",
"duration": "2"
}
let movies = [{
"genre" : "Action",
"people": {
"director": "Bob",
"writer": "Alice"
}
"boxoffice": "9,000,000",
"duration": "2"
},
{
"genre" : "Comedy",
"people": {
"director": "Rose",
"writer": "Mike"
}
"boxoffice": "12,000,000",
"duration": "3"
}]
我遇到的问题是,因为一些过滤器(如genre
过滤器)在 arrays 中,而一些电影键(如people
)嵌套在 object 中,我被迫在循环中嵌套循环,这使得时间复杂度增加。
我可以改变过滤器的结构方式,但它目前的方式对我来说是有意义的。 电影 object 格式是我无法更改的。
任何关于我如何解决这个问题的建议将不胜感激。
可以使用filter
方法和some
方法来完成:
let movieFilter = { "genre": ["Action", "Romance"], "director": "Bob", "writer": ["Jim", "Dave", "Alice"], "duration": "2" } let movies = [ { "genre": "Action", "people": { "director": "Bob", "writer": "Alice" }, "boxoffice": "9,000,000", "duration": "2" }, { "genre": "Comedy", "people": { "director": "Rose", "writer": "Mike" }, "boxoffice": "12,000,000", "duration": "3" }] const result = movies.filter(f => movieFilter.genre.some(ge=> ge == f.genre) && movieFilter.director == f.people.director && movieFilter.writer.some(wr => wr == f.people.writer) && movieFilter.duration == f.duration ); console.log(result);
更新:
感谢@MkeSpaGuy 评论。 我已经重新设计了一些过滤您的项目的方法。
略优化版本,使用key
检查过滤条件是否满足:
let movieFilter = { "genre": ["Action", "Romance"], "director": "Bob", "writer": ["Jim", "Dave", "Alice"], "duration": "2" } movieFilter.genre = movieFilter.genre.reduce((a, key) => ({...a, [key]: 1}), {}); movieFilter.writer = movieFilter.writer.reduce((a, key) => ({...a, [key]: 1}), {}); let movies = [{ "genre": "Action", "people": { "director": "Bob", "writer": "Alice" }, "boxoffice": "9,000,000", "duration": "2" }, { "genre": "Comedy", "people": { "director": "Rose", "writer": "Mike" }, "boxoffice": "12,000,000", "duration": "3" }]; const result = movies.filter(f => movieFilter.genre[f.genre] && movieFilter.director == f.people.director && movieFilter.writer[f.people.writer] && movieFilter.duration == f.duration ); console.log(result);
考虑用你的movieFilter中的对象替换你的arrays。
let movieFilter = { genre: { Action: true, Romance: true }, director: "Bob", writer: { Jim: true, Dave: true, Alice: true }, duration: "2" }; let movies = [ { genre: "Action", people: { director: "Bob", writer: "Alice" }, boxoffice: "9,000,000", duration: "2" }, { genre: "Comedy", people: { director: "Rose", writer: "Mike" }, boxoffice: "12,000,000", duration: "3" } ]; const filterOnMovieFilter = movie => { const { genre, people, duration } = movie; const { writer, director } = people || {}; return ( movieFilter.genre[genre] && movieFilter.writer[writer] && movieFilter.duration === duration && movieFilter.director === director ); }; console.log(movies.filter(filterOnMovieFilter));
但是,请避免过早优化。 在现代浏览器中过滤 10,000 个项目时,您不会注意到优化。
(注意我说的是过滤而不是显示)我经常做一些效率较低的事情,以支持简单、简洁、不可变、可读和有用的代码。 如果您的目标是功能手机或发现真正的性能瓶颈,则需要使用性能监控工具进行测量。 JavaScript 引擎优化不断改进,结果往往令人惊讶。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.