Элегантный способ сделать фильтр нескольких параметров для поиска на стороне клиента - PullRequest
0 голосов
/ 24 января 2020

Итак, скажем, у меня есть объект, который выглядит следующим образом:

const DEVICES: { mac: string; name: string; ip: string; type: number }[] = [
  {
    mac: 'xx:xx:xx:xx:xx',
    name: 'something',
    ip: 'xx.xx.xx.xx.xx',
    type: 0,
  },
  {
    mac: 'xx:xx:xx:xx:yy',
    name: 'something1',
    ip: 'xx.xx.xx.xx.yy',
    type: 1,
  },
  // and so on...
];

Когда я хотел иметь несколько параметров для поиска (name, ma c, ip) - для меня интуитивно понятно поместите несколько || (ИЛИ) в мою функцию фильтра, например:

 DEVICES.filter((item) => {
   return item.name.toLowerCase().indexOf(dataFromInputEvent.trim().toLowerCase()) >= 0
          || item.ip.toLowerCase().indexOf(dataFromInputEvent.trim().toLowerCase()) >= 0
          || item.mac.toLowerCase().indexOf(dataFromInputEvent.trim().toLowerCase()) >= 0;
 })
 .map(item, index) = {
   return (
     <SomeComponent
       key={index}
       type={item.type}
       name={item.name}
       mac={item.mac}
       type={item.type}
     />
   );
 )}

, как вы можете видеть, если данные получат больше свойств и если я добавлю другой параметр для поиска, я просто добавлю другой || внутри функции фильтра для возврата. Есть ли более элегантный способ поиска по нескольким параметрам - в идеале, без повторения одинаковых toLowerCase() и indexOf()? или, может быть, вообще не занимаюсь ||?

1 Ответ

3 голосов
/ 24 января 2020

Создайте массив свойств для фильтрации (в настоящее время ['name', 'ip', 'mac']), затем выполните итерации по ним и посмотрите, включают ли в .some из них, при обращении с помощью скобок в item, данные:

DEVICES.filter((item) => {
  const input = dataFromInputEvent.trim().toLowerCase();
  return ['name', 'ip', 'mac'].some(prop => item[prop].toLowerCase().includes(input));
})
.map( // ...

(обратите внимание, что вы можете сделать код гораздо менее повторяющимся, сохранив сначала обрезанный и введенный в нижний регистр ввод в переменной и используя .includes вместо indexOf)

Вы также вероятно, намеревался напечатать DEVICES как массив объектов, а не как один объект:

const DEVICES: Array<{ mac: string; name: string; ip: string; type: number }> = [

Но Typescript может почти выводить типы без необходимости явно их отмечать, поэтому

const DEVICES = [

Одного, вероятно, будет достаточно. (меньше кода для записи означает меньшую площадь поверхности для ошибок, и часто также делает вещи более читабельными)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...