Переключение массив фильтров


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

Что бы вы предложили это лучший способ, чтобы написать следующий императивный подход декларативно?

var selectedFilters = [ {name:"SomeName"} , ... ]
var inputFilter = {name:"OtherName"};

var indexFound = -1;
for (let i = 0; i < selectedFilters.length; i++) {
    if (selectedFilters[i].name === inputFilter.name) {
        indexFound = i;
    }
}

if (indexFound != -1) {
    selectedFilters.splice(indexFound, 1);
} else {
    selectedFilters.push(inputFilter);
}

Идея была бы использовать фильтр, чтобы отсеять элемента, если он существует по имени, то если результирующего массива равен исходному, нажмите. Но он все еще не по себе.



173
2
задан 27 марта 2018 в 11:03 Источник Поделиться
Комментарии
3 ответа

Чистое Состояние В

Есть два пути вы можете сделать это.

Чисто

Первый функциональный чистый способ первый копирует массив, затем проверяет, если элемент для переключения существует, в зависимости от этого результата добавляет или удаляет элемент. Убедившись, что добавленного элемента-это копия, а не ссылка. Он не имеет побочных эффектов, но требует дополнительных циклов памяти и процессора.

const toggleItem = (itemDesc, items, prop = "name") => {
items = [...items];
const index = items.findIndex(item => itemDesc[prop] === item[prop]);
index > -1 ? items.splice(index, 1) : items.push({...itemDesc});
return items;
}

Государство

Второй не создает новый массив и сохраняет все ссылки это "функционально" нечистые и гарантирует, что измененные состояния доступен для всех отсылок к оригиналу. Это значительно быстрее и использует меньше памяти.

const toggleItem = (itemDesc, items, prop = "name") => {
const index = items.findIndex(item => itemDesc[prop] === item[prop]);
index > -1 ? items.splice(index, 1) : items.push(itemDesc);
return items;
}

2
ответ дан 27 марта 2018 в 01:03 Источник Поделиться

Здесь представлена функциональная версия. JavaScript имеет довольно много функциональных функций, которые могут помочь вам здесь. Он мог бы, вероятно, сделал бы даже лучше, но это был мой первый подход

function updateFilters(currentFilters, newFilter) {
const hasName = filter => filter.name === newFilter.name;
const foundIndex = currentFilters.findIndex(hasName);

return foundIndex === -1
? currentFilters.concat([newFilter])
: currentFilters.splice(foundIndex, 1);
}

1
ответ дан 27 марта 2018 в 11:03 Источник Поделиться

Почему не просто фильтр с selectedFilters.filter(predName(inputFilter)) с сказуемым predName = ({name: filterName}) => ({name}) => name === filterName.

0
ответ дан 27 марта 2018 в 12:03 Источник Поделиться