简体   繁体   English

如何使用lodash使用值数组过滤嵌套对象?

[英]How can I filter a nested object with an array of values using lodash?

I have the following data: 我有以下数据:

var jobs = [
{
 job_type: "Part Time",
 latitude: 49.545068,
 longitude: 0.760518,
 title: "reiciendis",
 industry: [
  {
    id: 1,
    name: "development" },
  { 
    id: 2,
    name: "design"
  }
 ]},
{
 job_type: "Full Time",
 latitude: 51.545068,
 longitude: 0.460518,
 title: "auteas",
 industry: [
  {
    id: 1,
    name: "development" },
  { 
    id: 2,
    name: "testing"
  }
 ]

and I'd like to try and filter the results based on a users search parameters, namely the choice of industries for a job search, which populate an array: 并且我想尝试根据用户搜索参数(即选择职位的行业选择)过滤结果,这些参数会填充一个数组:

var jobchoices = ["testing", "design"];

my lodash filter so far looks like this: 到目前为止,我的lodash过滤器如下所示:

var self = this

return _.filter(this.jobs, function(item) {
    return _.filter(item.industry, function(obj) {
        return _.some(self.jobchoices, obj.name);
    });
});

but it returns true for all jobs. 但对于所有作业,它都返回true。 This is my first time using lodash. 这是我第一次使用lodash。 What am I doing wrong? 我究竟做错了什么? Secondly, could I continue chaining in this fashion to filter by another user choice, say by job type? 其次,我是否可以继续以这种方式链接以按另一个用户选择(例如,按工作类型)进行筛选?

You can use _.filter for the main array you are trying to retrieve as the end result and then use _.chain with _.map and _.intersection to filter the internal the objects array. 您可以将_.filter用作要尝试获取的最终结果的主数组,然后将_.chain与_.map和_.intersection一起使用以过滤内部对象数组。

Something like the code bellow should suffice, although it is not pretty. 尽管不是很漂亮,但是类似下面的代码就足够了。

var self = this;

_.filter(jobs, function(job) { 

  return _.chain(job.industry)
    .map('name')
    .intersection(self.jobchoices)
    .size()
    .gt(0)
    .value() 
})

(Tested only with latest lodash - v4.16.4) (仅在最新的lodash-v4.16.4中进行了测试)

It should return true for all jobs, because both jobs in your example data jobs have matching industry items. 对于所有作业,它应该返回true,因为示例数据jobs两个jobs都具有匹配的industry项目。 If you change your jobchoices array to have an item (or multiple items) that only match one of your jobs , that could look something like this (vanilla JS): 如果将jobchoices数组更改为一个(或多个)项仅与您的一项jobs匹配,则可能看起来像这样(香草JS):

var matches = jobs.filter(function(job) {
  return job.industry.some(function(industry) {
    return jobchoices.indexOf(industry.name) > -1;
  });
});

Or the ES6 equivalent: 或等效于ES6:

let matches = jobs.filter(({industry} => industry.some(({name}) => jobchoices.includes(name)));

As to where you are going wrong, your top-level _.filter is returning another _.filter (which will return an array - and is truthy - therefore all items will be returned). 至于哪里出了问题,顶级_.filter将返回另一个_.filter (它将返回一个数组- 是真实的 -因此将返回所有项目)。 You should be able to modify your original code return whether the inner _.filter call's length is > 0 to remedy: 无论内部_.filter调用的长度是否> 0 ,您都应该能够修改原始代码以进行补救:

return _.filter(this.jobs, function(item) {
    var matchingIndustries = _.filter(item.industry, function(obj) {
        return _.some(self.jobchoices, obj.name);
    });
    return matchingIndustries.length > 0;
});

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

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