프로그래밍 언어/HTML,CSS,JS

HTMLCollection 요소에 대한 For 루프

Rateye 2021. 8. 11. 11:23
728x90
반응형
질문 : HTMLCollection 요소에 대한 For 루프

HTMLCollectionOf 의 모든 요소에 대한 ID 가져 오기를 설정하려고합니다. 다음 코드를 작성했습니다.

var list = document.getElementsByClassName("events");
console.log(list[0].id);
for (key in list) {
    console.log(key.id);
}

하지만 콘솔에 다음과 같은 출력이 나타납니다.

event1
undefined

내가 기대했던 것이 아닙니다. 두 번째 콘솔 출력이 undefined 않았지만 첫 번째 콘솔 출력이 event1 이유는 무엇입니까?

답변

원래 질문에 대한 응답으로 for/in 잘못 사용하고 있습니다. 코드에서 key 는 색인입니다. 따라서 의사 배열에서 값을 얻으려면 list[key] 를 수행하고 id를 얻으려면 list[key].id 수행해야합니다. 그러나 처음부터 for/in 으로이 작업을 수행해서는 안됩니다.

요약 (2018 년 12 월에 추가됨)

for/in 을 사용하여 nodeList 또는 HTMLCollection을 반복하지 마십시오. 이를 피해야하는 이유는 다음과 같습니다.

최신 버전의 모든 최신 브라우저 (Safari, Firefox, Chrome, Edge)는 모두 nodeList 또는 HTMLCollection 과 같은 DOM 목록 for/of 반복을 지원합니다.

예를 들면 다음과 같습니다.

var list = document.getElementsByClassName("events");
for (let item of list) {
    console.log(item.id);
}

이전 브라우저 (IE 등 포함)를 포함하려면 다음과 같이 모든 곳에서 작동합니다.

var list= document.getElementsByClassName("events");
for (var i = 0; i < list.length; i++) {
    console.log(list[i].id); //second console output
}

for/in 사용하지 말아야하는 이유에 대한 설명

for/in 은 객체의 속성을 반복하기위한 것입니다. 즉, 객체의 모든 반복 가능한 속성을 반환합니다. 배열 (배열 요소 또는 의사 배열 요소 반환)에 대해 작동하는 것처럼 보일 수 있지만 배열과 유사한 요소에서 기대하지 않는 객체의 다른 속성을 반환 할 수도 있습니다. 그리고 HTMLCollection 또는 nodeList for/in 반복으로 반환되는 다른 속성을 가질 수 있습니다. 방금 Chrome에서 이것을 시도하고 반복하는 방식으로 반복하면 목록의 항목 (인덱스 0, 1, 2 등)을 검색하지만 lengthitem 속성도 검색합니다. for/in 반복은 HTMLCollection에서 작동하지 않습니다.

for/in HTMLCollection을 반복 할 수없는 이유는 http://jsfiddle.net/jfriend00/FzZ2H/ 를 참조하십시오.

Firefox에서 for/in 반복은 다음 항목 (객체의 모든 반복 가능한 속성)을 반환합니다.

0
1
2
item
namedItem
@@iterator
length

for (var i = 0; i < list.length; i++) 대신 사용하려는 이유를 알 수 있으므로 반복에서 0 , 12 를 얻습니다.

다음은 반복 할 수있는 추가 방법을 제공하는 2015-2018 기간 동안 브라우저가 진화 한 방식입니다. 위에서 설명한 옵션을 사용할 수 있으므로 최신 브라우저에서는 이러한 옵션이 필요하지 않습니다.

2015 년 ES6 업데이트

ES6에 추가 된 것은 배열과 유사한 구조를 실제 배열로 변환하는 Array.from() 이를 통해 다음과 같이 목록을 직접 열거 할 수 있습니다.

"use strict";

Array.from(document.getElementsByClassName("events")).forEach(function(item) {
   console.log(item.id);
});

작동 데모 (2016 년 4 월 현재 Firefox, Chrome 및 Edge) : https://jsfiddle.net/jfriend00/8ar4xn2s/

2016 년 ES6 업데이트

이제 코드에 다음을 추가 NodeListHTMLCollection 과 함께 ES6 for / of 구문을 사용할 수 있습니다.

NodeList.prototype[Symbol.iterator] = Array.prototype[Symbol.iterator];
HTMLCollection.prototype[Symbol.iterator] = Array.prototype[Symbol.iterator];

그런 다음 다음을 수행 할 수 있습니다.

var list = document.getElementsByClassName("events");
for (var item of list) {
    console.log(item.id);
}

이것은 Chrome, Firefox 및 Edge의 현재 버전에서 작동합니다. 이는 NodeList 및 HTMLCollection 프로토 타입 모두에 Array 반복기를 연결하여 for / of가 반복 할 때 Array 반복기를 사용하여 반복하기 때문에 작동합니다.

작업 데모 : http://jsfiddle.net/jfriend00/joy06u4e/ .

2016 년 12 월 ES6의 두 번째 업데이트

2016 년 12 월부터 Symbol.iterator 지원이 Chrome v54 및 Firefox v50에 내장되어 있으므로 아래 코드는 저절로 작동합니다. 아직 Edge에 내장되어 있지 않습니다.

var list = document.getElementsByClassName("events");
for (let item of list) {
    console.log(item.id);
}

작동 데모 (Chrome 및 Firefox) : http://jsfiddle.net/jfriend00/3ddpz8sp/

2017 년 12 월 ES6의 세 번째 업데이트

12 월 2017,이 기능은 대한 에지 41.16299.15.0에서 작동 nodeList 에서와 같이 document.querySelectorAll() ,하지만이 아닌 HTMLCollection 같이 document.getElementsByClassName() 수동을 위해 가장자리에서 사용하는 반복자를 할당해야하므로 HTMLCollection . 한 컬렉션 유형을 수정했지만 다른 컬렉션 유형은 수정하지 않은 이유는 완전히 미스터리입니다. 그러나 최소한 현재 버전의 Edge에서 for/of 구문과 함께 document.querySelectorAll() 의 결과를 사용할 수 있습니다.

또한 위의 jsFiddle을 업데이트하여 HTMLCollectionnodeList 별도로 테스트하고 jsFiddle 자체의 출력을 캡처합니다.

2018 년 3 월 ES6의 네 번째 업데이트

mesqueeeb에 따라 Symbol.iterator 지원이 Safari에도 내장되어 있으므로 document.getElementsByClassName() 또는 document.querySelectorAll() for (let item of list) 를 사용할 수 있습니다.

2018 년 4 월 ES6에 대한 다섯 번째 업데이트

for/of HTMLCollection 을 반복하는 지원은 2018 년 가을 Edge 18에 제공 될 것입니다.

2018 년 11 월 ES6 6 번째 업데이트

Microsoft Edge v18 (2018 년 가을 Windows 업데이트에 포함됨)을 사용하면 이제 Edge에서 for / of를 사용하여 HTMLCollection과 NodeList를 모두 반복 할 수 있음을 확인할 수 있습니다.

따라서 이제 모든 최신 브라우저에는 HTMLCollection 및 NodeList 개체 for/of

출처 : https://stackoverflow.com/questions/22754315/for-loop-for-htmlcollection-elements
728x90
반응형