#javascript #arrays #typescript #ecmascript-2020 #ecmascript-2021
Вопрос:
У меня есть массив с некоторым элементом, который я хочу проверить, существует ли в массиве какая-либо комбинация элементов, за которой следует целевой элемент любого элемента checkingSet, если да, то верните true, в противном случае верните false. Например, если inputArray равен [«a», «b», «c», «d»], а поиск комбинации равен [«a», «d»], то он должен возвращать значение true, потому что inputArray содержит оба в правильной последовательности. если inputArray [‘d’, ‘b’, ‘c’, ‘d’, ‘a’] и комбинация [‘a’, ‘d’], то она должна быть ложной, потому что inputArray включает оба элемента, но в неправильном порядке или
isExist(['a', 'd']) => true
isExist(['a', 'a', 'd']) => true
isExist(['e', 'd']) => false
Я могу использовать цикл Set и while
, но мне интересно, есть ли более элегантный или современный способ сделать это?
export function isExist(checkArray): boolean {
let hasA = false;
let hasB = false;
checkingSet = new Set(['b', 'c', 'd'])
const target = 'a'
inputArray = [...checkArray]
while (inputArray amp;amp; !!inputArray.length) {
const lastOne = inputArray.pop();
if (!hasA amp;amp; !!lastOne) {
hasA = chekcingSet.has(lastOne);
}
if (!hasB amp;amp; !!lastOne) {
hasB = lastOne === target;
}
if (hasA amp;amp; hasB) {
return true;
}
}
return false;
}
Комментарии:
1. Я не думаю, что понял, какого результата вы ожидаете. Как это верно для a,d,когда множество равно b,c, d
2. Что такое
target
? И почемуcheckingSet
определяется внутри функции, а не передается в качестве аргумента?3. Не могли бы вы немного лучше объяснить, что на самом деле пытается сделать ваш метод.
4. Почему вы используете двойной восклицательный знак (!!)?
5. обновлено,@Snirka нужно убедиться, что pop существует
Ответ №1:
Чтобы проверить , что массив содержит 'a'
, и после этого 'a'
хотя бы один из ['b', 'c', 'd']
них находится в массиве, вы можете сделать это. Сначала получите индекс первого 'a'
в массиве, затем проверьте, включено ли ['b', 'c', 'd']
какое-либо значение в этот массив после этого начального индекса.
function doesExist(arr) {
const startPos = arr.indexOf('a')
if (startPos < 0)
return false
return ['b', 'c', 'd'].some(char => arr.includes(char, startPos 1))
}
console.log(doesExist(['a', 'd']))
console.log(doesExist(['a', 'a', 'd']))
console.log(doesExist(['e', 'd']))
console.log(doesExist(['d', 'a']))
Ответ №2:
Это общая версия, это O(n).
function doesDupleExistInOrder([el1, el2], arr) {
let index = arr.indexOf(el1)
if (index == -1) return false;
return arr.includes(el2, index 1)
}
console.log(doesDupleExistInOrder(["a", "d"], ["a", "b", "c", "d", "e"])); // true
console.log(doesDupleExistInOrder(["a", "b"], ["a", "b", "c", "d", "e"])); // true
console.log(doesDupleExistInOrder(["d", "e"], ["a", "b", "c", "d", "e"])); // true
console.log(doesDupleExistInOrder(["d", "a"], ["a", "b", "c", "d", "e"])); // false
console.log(doesDupleExistInOrder(["d", "a"], ["a"])); // false
console.log(doesDupleExistInOrder(["d", "a"], [])); // false
Если вам нужна конкретная версия, просто выберите общую функцию, она же:
let doesADExist = arr => doesDupleExistInOrder(["a", "d"], arr);
console.log(doesADExist(["a", "b", "c", "d", "e"])); // true
Комментарии:
1. Я думаю, что если вы используете
arr.indexOf(el1)
для получения первого i (и проверки на -1), а затемarr.includes(el2, i 1)
это будет немного короче и легче читать2. @A_A, возможно, но для этого требуется два цикла по массиву, в худшем случае для этого требуется только один. Кроме того, это всего 5 строк, так что любой разумный программист мог бы понять, что это делает менее чем за минуту, и это более быстрый алгоритм.
3. Я так не думаю. Насколько я понимаю
indexOf(el1)
, он будет повторяться до тех пор, пока не найдет элемент по некоторому индексуi
. Иarr.includes(el2, i 1)
начал бы повторять в позицииi 1
. Так что в худшем случае это должно быть n шагов (и наверняка еще O(n)). Также эти методы могут быть оптимизированы браузером, но я не уверен в этом4. Хм, ладно, я забыл, что вы можете подключить индекс для включений. Я отредактирую свой пост.