JavaScript에서 Array.map으로 요소 제거
map()
함수 를 사용하여 항목 배열을 필터링하고 싶습니다 . 다음은 코드 조각입니다.
var filteredItems = items.map(function(item)
{
if( ...some condition... )
{
return item;
}
});
문제는 필터링 된 항목이 여전히 배열의 공간을 사용하므로 완전히 지우고 싶습니다.
어떤 생각?
편집 : 덕분에, 나는 약 잊고 filter()
, 내가 원하는 것은 사실이다 filter()
다음 map()
.
EDIT2 : 그 지적에 대한 감사 map()
및 filter()
내 특정 코드가 브라우저에서 실행하도록 구성되지 않았지만, 모든 브라우저에서 구현되지 않습니다.
filter
필터링 외에도 배열의 항목을 변경하려는 경우가 아니라면 매핑보다는 메서드를 사용해야합니다 .
예.
var filteredItems = items.filter(function(item)
{
return ...some condition...;
});
[편집 : 물론 당신은 항상 sourceArray.filter(...).map(...)
필터링과 돌연변이 모두 할 수 있습니다 ]
얼마 전에 답을 썼는데 의견이 바뀌 었습니다. 이 주제를 확장하고 훨씬 더 잘 설명하는 내 블로그 게시물 을 확인하는 것이 좋습니다 . 또한 대안의 끝에서 JSperf 비교를 제공합니다.
tl; dr은 다음과 같습니다. 원하는 것을 수행하려면 (한 함수 호출 내에서 필터링 및 매핑)Array.reduce()
. 그러나, 더 읽기 와 보통 빨리 이 접근 방식은 사용 필터이며 서로 연결하는지도 :
[1,2,3].filter(num => num > 2).map(num => num * 2)
다음은 Array.reduce()
작동 방식과이를 사용하여 한 번의 반복으로 필터 및 매핑을 수행하는 방법에 대한 설명입니다 . 이것이 너무 요약 된 경우, 위에 링크 된 블로그 게시물을 보는 것이 좋습니다. 이는 명확한 예제와 진행 과정이 포함 된 훨씬 더 친숙한 소개입니다.
(일반적으로 익명) 함수 인 인수를 줄입니다.
이 익명 함수 는 두 개의 매개 변수를 사용합니다. 하나 (map / filter / forEach에 전달 된 익명 함수)는 작동 할 반복자입니다. 그러나이를 줄이기 위해 전달 된 익명 함수에 대한 또 다른 인수가 있는데, 이러한 함수는 허용하지 않으며 , 이는 종종 memo 라고하는 함수 호출 사이에 전달 될 값입니다 .
Array.filter ()는 하나의 인수 (함수) 만 사용하는 반면 Array.reduce ()는 중요한 (선택 사항이지만) 두 번째 인수도 사용합니다. 첫 번째 인수이며 이후에 함수 호출 사이에 변경되어 전달 될 수 있습니다. (제공되지 않은 경우 첫 번째 익명 함수 호출의 'memo'는 기본적으로 첫 번째 iteratee가되고 'iteratee'인수는 실제로 배열의 두 번째 값이됩니다.)
우리의 경우, 시작하기 위해 빈 배열을 전달한 다음, 함수를 기반으로 배열에 iteratee를 삽입할지 여부를 선택합니다. 이것이 필터링 프로세스입니다.
마지막으로 각 익명 함수 호출에서 '진행중인 배열'을 반환하고, reduce는 해당 반환 값을 가져 와서 다음 함수 호출에 인수 (메모라고 함)로 전달합니다.
이를 통해 필터와 맵이 한 번의 반복으로 발생하여 필요한 반복 횟수를 절반으로 줄일 수 있습니다. :)
자세한 설명은 MDN 또는 위의 링크를 참조하십시오 . :)
Reduce 호출의 기본 예 :
let array = [1,2,3];
const initialMemo = [];
array = array.reduce((memo, iteratee) => {
// if condition is our filter
if (iteratee > 1) {
// what happens inside the filter is the map
memo.push(iteratee * 2);
}
// this return value will be passed in as the 'memo' argument
// to the next call of this function, and this function will have
// every element passed into it at some point.
return memo;
}, initialMemo)
console.log(array) // [4,6], equivalent to [(2 * 2), (3 * 2)]
더 간결한 버전 :
[1,2,3].reduce((memo, value) => value > 1 ? memo.concat(value * 2) : memo, [])
첫 번째 iteratee는 1보다 크지 않으므로 필터링되었습니다. 또한 그 존재를 명확하게하고 관심을 끌기 위해 이름이 지정된 initialMemo에 주목하십시오. 다시 한 번, 첫 번째 익명 함수 호출에 'memo'로 전달되고 익명 함수의 반환 된 값은 다음 함수에 'memo'인수로 전달됩니다.
메모에 대한 고전적인 사용 사례의 또 다른 예는 배열에서 가장 작거나 가장 큰 숫자를 반환하는 것입니다. 예:
[7,4,1,99,57,2,1,100].reduce((memo, val) => memo > val ? memo : val)
// ^this would return the largest number in the list.
자신의 감소 함수를 작성하는 방법의 예 (이는 종종 다음과 같은 함수를 이해하는 데 도움이됩니다.)
test_arr = [];
// we accept an anonymous function, and an optional 'initial memo' value.
test_arr.my_reducer = function(reduceFunc, initialMemo) {
// if we did not pass in a second argument, then our first memo value
// will be whatever is in index zero. (Otherwise, it will
// be that second argument.)
const initialMemoIsIndexZero = arguments.length < 2;
// here we use that logic to set the memo value accordingly.
let memo = initialMemoIsIndexZero ? this[0] : initialMemo;
// here we use that same boolean to decide whether the first
// value we pass in as iteratee is either the first or second
// element
const initialIteratee = initialMemoIsIndexZero ? 1 : 0;
for (var i = initialIteratee; i < this.length; i++) {
// memo is either the argument passed in above, or the
// first item in the list. initialIteratee is either the
// first item in the list, or the second item in the list.
memo = reduceFunc(memo, this[i]);
}
// after we've compressed the array into a single value,
// we return it.
return memo;
}
예를 들어 실제 구현에서는 인덱스와 같은 항목에 액세스 할 수 있지만 이것이 요점에 대한 복잡하지 않은 느낌을 얻는 데 도움이되기를 바랍니다.
그것은지도가하는 일이 아닙니다. 정말 Array.filter 원합니다 . 또는 원래 목록에서 요소를 정말로 제거하려면 for 루프를 사용하여 명령 적으로 수행해야합니다.
배열 필터 방법
var arr = [1, 2, 3]
// ES5 syntax
arr = arr.filter(function(item){ return item != 3 })
// ES2015 syntax
arr = arr.filter(item => item != 3)
console.log( arr )
그러나은 Array.filter
모든 브라우저에서 지원되지 않으므로 프로토 타입을 작성해야합니다.
//This prototype is provided by the Mozilla foundation and
//is distributed under the MIT license.
//http://www.ibiblio.org/pub/Linux/LICENSES/mit.license
if (!Array.prototype.filter)
{
Array.prototype.filter = function(fun /*, thisp*/)
{
var len = this.length;
if (typeof fun != "function")
throw new TypeError();
var res = new Array();
var thisp = arguments[1];
for (var i = 0; i < len; i++)
{
if (i in this)
{
var val = this[i]; // in case fun mutates this
if (fun.call(thisp, val, i, this))
res.push(val);
}
}
return res;
};
}
그렇게하면 필요한 모든 메서드를 프로토 타입 할 수 있습니다.
following statement cleans object using map function.
var arraytoclean = [{v:65, toberemoved:"gronf"}, {v:12, toberemoved:null}, {v:4}];
arraytoclean.map((x,i)=>x.toberemoved=undefined);
console.dir(arraytoclean);
참고URL : https://stackoverflow.com/questions/9289/removing-elements-with-array-map-in-javascript
'developer tip' 카테고리의 다른 글
angularjs ui-router의 상태간에 $ scope 데이터를 공유하려면 어떻게해야합니까? (0) | 2020.10.29 |
---|---|
C ++ std :: ref (T)와 T &의 차이점은 무엇입니까? (0) | 2020.10.29 |
JMS의 장점은 무엇입니까? (0) | 2020.10.29 |
WPF 확인란 바인딩 (0) | 2020.10.29 |
리플렉션을 통해 한 클래스의 필드에서 다른 클래스로 모든 값 복사 (0) | 2020.10.29 |