在纯Javascript中,尝试过滤包含用户对象的数组中的多个值,该用户对象包含其他对象和数组 [英] In plain Javascript, trying to filter for multiple values in an array that contains User objects that contain other objects and arrays

查看:41
本文介绍了在纯Javascript中,尝试过滤包含用户对象的数组中的多个值,该用户对象包含其他对象和数组的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

感谢您对此的关注.抱歉,长度太长了,想弄清楚!

thanks for taking a look at this. Sorry for length, trying to be clear!

我想做什么: 我有一个用户数组(每个用户一个对象),并尝试根据多个条件(来自法国的男性"或具有工程技术的西班牙和美国的女性"等)过滤用户,但到目前为止,事实证明,这超出了我的能力.

WHAT I'M TRYING TO DO: I have an array of users (each user an object) and am trying to filter the users on multiple criteria ("males from France" OR "females from Spain and United States with Engineering skills" etc) but it's proven beyond my skills so far.

困难的部分是用户是User数组中的对象,但是在每个用户对象中,某些值是其他对象或数组.用户数据数组如下所示(缩写):

The hard part has been that the users are objects within a User array, but within each user object, some values are additional objects or arrays. Here's what the user data array looks like (abbreviated):

let users = [
{ 
gender: 'male', 
location: {street: 'Clement Street', country: 'United States'},
skills: ['engineering', 'underwater'], 
}, ...

注意,性别只是正常的属性/值,但是国家/地区在位置对象之内,技能在一个数组之内.

Notice gender is just a normal property/value but country is within a location object and skills are within an array.

我已经有一个搜索按钮界面,该界面可以创建切换按钮来搜索每个可用的条件,并且每次单击按钮时,我都会在过滤器对象中添加或删除该条件.过滤器对象看起来像这样,并在其中使用数组,以便我可以一次定义多个条件,例如要搜索的多个国家/地区,多种技能等:

I already have a search button interface that creates toggle buttons to search on each criteria available, and every time you click a button, I add or remove that criteria in a filter object. The filter object looks like this, and uses arrays inside it so that I can define multiple criteria at once, like multiple countries to search, multiple skills, etc.:

    filter: {
        gender: ['female'],
    location: {
    country: ['Spain'],},
    skills: ['optics', ]
    },

我真正被困的地方 我创建了一个filterData方法,该方法可以成功基于性别(男性或女性)进行过滤,但无法通过国家(在位置对象中)或技能(在技能数组中)对ALSO进行过滤.我当前的filterData方法每个用户只经历一次迭代,但是我已经尝试过For循环和forEach尝试通过每个过滤器的标准(西班牙",光学"),但这只是行不通.我只有性别.

WHERE I REALLY GET STUCK I've created a filterData method that can successfully filter based on Gender (male or female) but can't get it to ALSO filter on country (within the location object) or skills (within the skills array). My current filterData method only goes through one iteration per user, but I've tried For loops and forEach to try to go through each of the filter's criteria ('Spain', 'Optics'), but it just doesn't work. I only get gender.

我认为我有两个问题:1)在某种程度上在代码中传达出,键"项不是值,而是必须在其中搜索的对象或数组,以及2)创建某种循环行为将通过每个过滤条件,而不是在第一个条件(性别)之后停止.

I think I have two problems: 1) somehow conveying in the code that the item 'key' in some cases will not be a value, but an object or array that must also be searched within, and 2) creating some kind of looping behavior that will go through each of the filter criteria, instead of stopping after the first one (gender).

这显然在我头上,所以任何指导或建议都将不胜感激,非常感谢!这是我一直在使用的所有代码,包括我的filterData方法.

That's apparently over my head right now, so any guidance or suggestions would be appreciated, thanks very much! And here's all the code I've been working with, including my filterData method.

var filtering = {
  filter: {
    gender: ["female"],
    location: {
      country: ["Spain"],
    },
    skills: ["optics"],
  },

  users: [
    {
      gender: "male",
      name: "John",
      location: { street: "Clement Street", country: "United States" },
      skills: ["engineering", "underwater"],
    },

    {
      gender: "female",
      name: "Mary",
      location: { street: "5th Avenue", country: "Spain" },
      skills: ["confidence", "optics"],
    },

    {
      gender: "male",
      name: "David",
      location: { street: "Vermont Ave", country: "France" },
      skills: ["cards", "metalurgy", "confidence"],
    },

    {
      gender: "female",
      name: "Rachel",
      location: { street: "Vermont Ave", country: "France" },
      skills: ["disguise", "electrical"],
    },

    {
      gender: "female",
      name: "Muriel",
      location: { street: "Vermont Ave", country: "Germany" },
      skills: ["flight", "surveillance"],
    },
  ],

  filterData: (filter) => {
    const filteredData = filtering.users.filter((item) => {
      for (let key in filter) {
        if (!filter[key].includes(item[key])) {
          return false;
        }
        return true;
      }
    });
    console.log(filteredData);
  },
};

filtering.filterData(filtering.filter);

推荐答案

有一个漂亮的技巧称为递归,它是一个自称函数.

There's a nifty trick called recursion, which is a function calling itself.

更新的代码为:checkUserfilterData

The updated code are: checkUserand filterData

var filtering = {
  filter: {
    gender: ["female"],
    location: {
      country: ["Spain"],
    },
    skills: ["optics"],
  },

  users: [
    {
      gender: "male",
      name: "John",
      location: { street: "Clement Street", country: "United States" },
      skills: ["engineering", "underwater"],
    },

    {
      gender: "female",
      name: "Mary",
      location: { street: "5th Avenue", country: "Spain" },
      skills: ["confidence", "optics"],
    },

    {
      gender: "male",
      name: "David",
      location: { street: "Vermont Ave", country: "France" },
      skills: ["cards", "metalurgy", "confidence"],
    },

    {
      gender: "female",
      name: "Rachel",
      location: { street: "Vermont Ave", country: "France" },
      skills: ["disguise", "electrical"],
    },

    {
      gender: "female",
      name: "Muriel",
      location: { street: "Vermont Ave", country: "Germany" },
      skills: ["flight", "surveillance"],
    },
  ],
  
  checkUser (filter, to_check) {
    if (Array.isArray(filter))
    {
      return Array.isArray(to_check)
        ? filter.some(val => to_check.includes(val)) // if what we're checking is an array
        : filter.includes(to_check); // otherwise it's a singular value
    }
    else
    {
      const all_checks = []; // this is to save every return value from the recursive function
      for (let key in filter) // going through each key in the filter
      {
        const checked = this.checkUser(filter[key], to_check[key]) // passing two values, which will be compared with each other
        all_checks.push(checked) // pushing the checked result
      }
      
      return all_checks.every(val => val) // checking that it passes the filter by ensuring every value is true
    }
  },

  filterData () {
    let filter = this.filter
    return this.users.filter(user => this.checkUser(filter, user))
  },
};

// filtering.filterData(filtering.filter);

// filtering.checkUser(filtering.filter, filtering.users[0])
const result = filtering.filterData()
console.log(result)

这篇关于在纯Javascript中,尝试过滤包含用户对象的数组中的多个值,该用户对象包含其他对象和数组的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆