If it's actually important to do the filtering in-place without creating another array, you have to go sort-of old school and iterate through the array with two indexes, copying values along the way. Every time you hit an element that fails the filter test, you increment one of the indexes but not the other one. At the end of that, you reset the array .length
to the trailing index:
function filterInPlace(array, fn) {
let from = 0, to = 0;
while (from < array.length) {
if (fn(array[from])) {
array[to] = array[from];
to++;
}
from++;
}
array.length = to;
}
This has the advantage of being O(n), with just one pass over the array, while the solutions involving .splice()
are O(n2).
To do your "range check", you could write another function to create a filter predicate given a minimum and a maximum value:
function rangePredicate(min, max) {
return n => n >= min && n <= max;
}
Then you can pass the return value of that to the filter function:
var arr = [1, 2, 3, ... ];
filterInPlace(arr, rangePredicate(0, 10));