-1

I have two arguments that are optional that I want to use to filter the array.

As they are optional i am using two if statements, but I am curious if there is a more efficient/shorthand way.

// initializing list of users
var users = [{
    name: 'John',
    email: 'johnson@mail.com',
    age: 25,
    address: 'USA'
  },
  {
    name: 'Tom',
    email: 'tom@mail.com',
    age: 35,
    address: 'England'
  },
  {
    name: 'Mark',
    email: 'mark@mail.com',
    age: 28,
    address: 'England'
  }
];


if (args.name){
    users = users.filter(x => x.name == args.name);
}

if (args.address){
    users = users.filter(x => x.address == args.address);
}

return users;
Dan Pettis
  • 113
  • 5
  • *"shorthand"*: isn't this short already? *"efficient"*: do you have a problem with timings? I mean, old-fashioned `for` loops are the fastest, but why would you? Moreover, questions about performance and style are more suitable for [Code Review](https://codereview.stackexchange.com/) – trincot Aug 15 '20 at 09:00
  • You can create a method and pass the parameter on what property you want to filter the data . – Harmandeep Singh Kalsi Aug 15 '20 at 09:01

4 Answers4

0

You could use the entries of args.

const entries = Object.entries(args);

return users.filter(user => entries.every(([k, v]) => user[k] === v));
Nina Scholz
  • 376,160
  • 25
  • 347
  • 392
0

Maybe this way?

if (args.name || args.address){
    users = users.filter(x => x.name == args.name || x.address == args.address);
}
Liu Lei
  • 1,256
  • 1
  • 9
  • 18
0

You could combine the conditionals into one filter statement to only walk through the array once:

function filter(args) {
// initializing list of users
var users = [{
    name: 'John',
    email: 'johnson@mail.com',
    age: 25,
    address: 'USA'
  },
  {
    name: 'Tom',
    email: 'tom@mail.com',
    age: 35,
    address: 'England'
  },
  {
    name: 'Mark',
    email: 'mark@mail.com',
    age: 28,
    address: 'England'
  }
];


let conditionals = [];

if (args.name){
    conditionals.push(x => x.name == args.name);
}

if (args.address){
    conditionals.push(x => x.address == args.address);    
}


return users.filter(x => conditionals.every(c => c(x));

}

Please bear in mind that the real-world impact of this optimisation is really low if you are not dealing with enormous amounts of data

Daniel Schmidt
  • 11,605
  • 5
  • 38
  • 70
0

You can create helper function for your needs and then use it in your code

const users = [{
    name: 'John',
    email: 'johnson@mail.com',
    age: 25,
    address: 'USA'
  },
  {
    name: 'Tom',
    email: 'tom@mail.com',
    age: 35,
    address: 'England'
  },
  {
    name: 'Mark',
    email: 'mark@mail.com',
    age: 28,
    address: 'England'
  }
];

// Filter function
const fltr = (obj, search) => {
  const res = [];
  for(let i = 0; i < obj.length; i++) {
    for(let key in search) {
      let add = true;
      for(let key in search) {
        if(obj[i][key] && obj[i][key] === search[key]) add = true;
        if(!obj[i][key] || obj[i][key] !== search[key]) {
          add = false;
          break;
        }
      }
      if(add) res.push(obj[i]);
    }
  }
  return res;
}

//
// Args
const args = {
  address: "England"
};

// Use your function in your code, fast and easy
const res = fltr(users, args);

// Log
console.log(res);
tarkh
  • 2,424
  • 1
  • 9
  • 12