HTML getElementsByClassName возвращает HTMLCollection длиной 0

Я пытаюсь использовать js document.getElementsByClassName чтобы найти элемент html, который на самом деле является заголовком таблицы.

для следующих кодов:

console.log(document.getElementsByClassName('gtableheader'));

С Firebug, Я вижу это log a HTMLCollection, и когда я нажимаю на него, он показывает:

-> 0         tr.gtableheader
   length    1

таким образом, он находит элемент, который я хочу.

но когда я через:

console.log(document.getElementsByClassName('gtableheader').length);

затем выводится 0. Это так странно, есть идеи насчет этого?

4 ответов


используя getElementsByClassName() вернет все элементы с этим именем класса в документе в качестве NodeList. Этот объект представляет коллекцию узлов, к которым можно получить доступ по индексным номерам, начинающимся с 0. Для доступа к элементам в NodeList вам придется использовать цикл.

когда вы console.log(document.getElementsByClassName('gtableheader').length); вы видите 0, потому что при его запуске нет элемента с class gtableheader. Вы можете видеть элементы в консоли, потому что document.getElementsByClassName() возвращает обновленную живую коллекцию при добавлении новых элементов.

кроме того, в коде, который вы используете, и длина равна 0, вы можете использовать код ниже для доступа к имени класса.

document.getElementsByClassName('gtableheader')[0].style.color="red";

если вы хотите получить доступ ко всем элементам класса, вы можете использовать цикл for.

var x = document.getElementsByClassName('gtableheader');
for (var i = 0; i < x.length; i++) {
    x[i].style.color = "red";
}

больше информации: http://www.w3schools.com/jsref/met_document_getelementsbyclassname.asp


вот так getElementsByClassName возвращает live коллекция. the length свойство объекта составляет 0 потому что в этот момент времени в DOM нет элемента с этим именем класса. Поскольку консоль показывает живое представление объекта, она показывает все соответствующие элементы при добавлении элементов в DOM.

DOM parser анализирует документы сверху вниз, когда он достигает тега, он анализирует его и добавляет его представление DOM (an пример HTMLElement интерфейс) к объектной модели документов. Вы должны либо переместить тег скрипта в конец body tag или слушать DOMContentLoaded событие, которое запускается, когда исходный HTML-документ был полностью загружен и обработан.


использовать это, чтобы заставить его работать

window.addEventListener("load", function(event) {
    console.log(document.getElementsByClassName('gtableheader').length);
});

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

что сработало для меня, так это обернуть код, который нуждался в массиве внутри MutationObserver и установить его для просмотра жестко закодированного div, содержащего разделы, которые будут динамически генерироваться (см. Это StackOverflow ответ и документация MDN).

попробуйте это:

var divArray = document.getElementById('hardCodedContainer');

var observer = new MutationObserver(function(){
   console.log(document.getElementsByClassName('gtableheader').length);
   console.log(document.getElementsByClassName('gtableheader'));
};

observer.observe(divArray, { attributes: false, childList: true, subtree: true });

// When you've got what you need, you should call this function to trigger a disconnect 
function classesFound(){
   observer.disconnect();
};