Как получить список активных элементов из массива? - PullRequest
0 голосов
/ 13 ноября 2018

Я пытаюсь получить список сотрудников, у которых есть только активные увлечения и роль которых принадлежит типу "А".

Я пытался использовать приведенный ниже запрос, но безуспешно.

Что я делаю не так?

// Get all the employees with active hobbies and have a role of 'A'
var employees = people.find(item => item.key === 'Employees').employees.map(emp => emp.hobbies).filter(hobby => hobby.filter(h => h.active === true && h.roles.includes('A')));

console.log(employees);
<script>
  var people = [{
    key: 'Employees',
    employees: [{
        name: 'joe',
        age: 20,
        hobbies: [{
          'active': true,
          name: 'skating',
          roles: ['C', 'A']
        }]
      },
      {
        name: 'amy',
        age: 32,
        hobbies: [{
          'active': true,
          name: 'surfing',
          roles: ['A']
        }]
      },
      {
        name: 'kate',
        age: 34,
        hobbies: [{
          'active': true,
          name: 'running',
          roles: ['C']
        }, {
          name: 'Chess',
          active: false,
          roles: ['C', 'A']
        }]
      }
    ]
  }];
</script>

Обновление

Когда я добавил в массив больше сотрудников с новыми увлечениями, принятый ответ не дал правильного результата. Почему это происходит?

var people = [{
        key: 'Employees',
        employees: [{
                name: 'Steve',
                age: 50,
                hobbies: [{
                        active: true,
                        name: 'skating',
                        roles: ['C', 'A']
                    },
                    {
                        active: false,
                        name: 'skating',
                        roles: ['C', 'A']
                    },
                    {
                        active: true,
                        name: 'snooker',
                        roles: ['C', 'A']
                    },
                    {
                        active: true,
                        name: 'darts',
                        roles: ['C', 'A']
                    }
                ]
            },{
                name: 'joe',
                age: 20,
                hobbies: [{
                        active: true,
                        name: 'skating',
                        roles: ['C', 'A']
                    }
                ]
            }, {
                name: 'amy',
                age: 32,
                hobbies: [{
                        'active': true,
                        name: 'surfing',
                        roles: ['A']
                    }
                ]
            }, {
                name: 'kate',
                age: 34,
                hobbies: [{
                        active: true,
                        name: 'running',
                        roles: ['C']
                    }, {
                        name: 'Chess',
                        active: false,
                        roles: ['C', 'A']
                    }
                ]
            }
        ]
    }
];

var employees = people.find(item => item.key === 'Employees').employees.filter(employee => employee.hobbies.every(h => h.active && h.roles.includes('A')));

Ответы [ 5 ]

0 голосов
/ 13 ноября 2018

Вы можете просто сделать один звонок на Array.prototype.filter, который проверяет условия, которые вы упомянули:

person.hobbies.every(y => y.active) && person.hobbies.every(z => z.roles.includes('A'))

var people = [{
  key: 'Employees',
  employees: [{
      name: 'joe',
      age: 20,
      hobbies: [{
        'active': true,
        name: 'skating',
        roles: ['C', 'A']
      }]
    },
    {
      name: 'amy',
      age: 32,
      hobbies: [{
        'active': true,
        name: 'surfing',
        roles: ['A']
      }]
    },
    {
      name: 'kate',
      age: 34,
      hobbies: [{
        'active': true,
        name: 'running',
        roles: ['C']
      }, {
        name: 'Chess',
        active: false,
        roles: ['C', 'A']
      }]
    }
  ]
}];

let employees = people[0].employees.filter(x => 
  x.hobbies.every(y => y.active) && x.hobbies.every(z => z.roles.includes('A'))
)

console.log(employees);
0 голосов
/ 13 ноября 2018

.map(emp => emp.hobbies) возвращает массив хобби, поэтому значение employees будет отфильтрованным списком хобби, а не сотрудников, у которых есть эти хобби.Вы должны фильтровать сотрудников, а не отображать их.

// Get all the employees with active hobbies and have a role of 'A'
var employees = people.find(item => item.key === 'Employees').employees.filter(emp =>
  emp.hobbies.every(h => h.active && h.roles.includes('A')));

console.log(employees);
<script>
  var people = [{
    key: 'Employees',
    employees: [{
        name: 'joe',
        age: 20,
        hobbies: [{
          'active': true,
          name: 'skating',
          roles: ['C', 'A']
        }]
      },
      {
        name: 'amy',
        age: 32,
        hobbies: [{
          'active': true,
          name: 'surfing',
          roles: ['A']
        }]
      },
      {
        name: 'kate',
        age: 34,
        hobbies: [{
          'active': true,
          name: 'running',
          roles: ['C']
        }, {
          name: 'Chess',
          active: false,
          roles: ['C', 'A']
        }]
      }
    ]
  }];
</script>
0 голосов
/ 13 ноября 2018

Вы можете использовать map & filter:

var people = [{ key: 'Employees', employees: [{ name: 'joe', age: 20, hobbies: [{ 'active': true, name: 'skating', roles: ['C', 'A'] }] }, { name: 'amy', age: 32, hobbies: [{ 'active': true, name: 'surfing', roles: ['A'] }] }, { name: 'kate', age: 34, hobbies: [{ 'active': true, name: 'running', roles: ['C'] }, { name: 'Chess', active: false, roles: ['C', 'A'] }] } ] }];

const result = people.filter(x => x.key == 'Employees')
  .map(({employees}) => 
  employees.filter(x => x.hobbies.some(y => y.active && y.roles.includes('A'))))

console.log(result)

Вы также можете использовать reduce & filter:

var people = [{ key: 'Employees', employees: [{ name: 'joe', age: 20, hobbies: [{ 'active': true, name: 'skating', roles: ['C', 'A'] }] }, { name: 'amy', age: 32, hobbies: [{ 'active': true, name: 'surfing', roles: ['A'] }] }, { name: 'kate', age: 34, hobbies: [{ 'active': true, name: 'running', roles: ['C'] }, { name: 'Chess', active: false, roles: ['C', 'A'] }] } ] }];

const result = people.filter(x => x.key == 'Employees').reduce((r,{employees}) => 
{
  r.push(employees.filter(x => 
  x.hobbies.some(y => y.active && y.roles.includes('A'))))
  return r
}, [])

console.log(result)
0 голосов
/ 13 ноября 2018

Ситуация идет не так, когда вы сопоставляете сотрудников с их хобби: ваш конечный результат будет состоять из хобби, а не сотрудников.

Вам необходимо придерживаться уровня сотрудника:

var people = [{key: 'Employees',employees: [{ name: 'joe', age: 20, hobbies: [{'active': true, name: 'skating', roles: ['C', 'A'] }] },{ name: 'amy', age: 32, hobbies: [{'active': true, name: 'surfing', roles: ['A'] }] }, { name: 'kate', age: 34, hobbies: [{'active': true, name: 'running', roles: ['C']}, {name: 'Chess', active: false, roles: ['C','A']}] }]}];

var employees = people.find(item => item.key === 'Employees').employees
    .filter(employee => employee.hobbies.every(h => h.active && h.roles.includes('A')));
        
console.log(employees);

В выражении нет необходимости сравнивать логическое свойство с true. Просто используйте свойство (active в данном случае).

Используйте .some вместо .every, если требуется, чтобы у сотрудников было как минимум одно такое хобби, вместо требования всех их хобби соответствовать условию.

0 голосов
/ 13 ноября 2018

Если вы сделаете это:

 .map(emp => emp.hobbies).filter(hobby =>

вы сопоставляете каждого сотрудника с его хобби, результатом которого является массив 2D:

 [[ { active: true }, { active: false } ], [/*...*/]]

Поэтому hobby - это не одно хобби , а множество хобби.

Вы сказали

Я пытаюсь получить список сотрудников

... что означает, что вы на самом деле не хотите .map увлечений, а скорее .filter сотрудников и проверки, если ever хобби удовлетворяет определенным правилам:

 const employees = people.find(({ key }) => key === "Employees").employees;

 const isActive = hobby => hobby.active && hobby.roles.includes("A");

 const result = employees.filter(emp => emp.hobbies.every(isActive));
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...