遍历DOM时访问NodeList/HTMLCollection元素返回undefined怎么办
问题根因
代码返回undefined和NodeList/HTMLCollection是否转数组、使用哪种循环写法没有任何关系,是两处基础逻辑错误导致的:
- 比对逻辑类型不匹配:
randomNumber存储的是<span id="theRandomNumber">对应的DOM元素对象,而prizeSections[i].dataset.id是字符串类型的自定义属性值,将DOM对象和字符串做全等判断永远无法匹配成功,循环执行完theSection始终是初始值null。 - DOM属性访问逻辑错误:通过
event.target.parentElement.parentElement.nextElementSibling获取到的是id为bottomOfPage的div节点,后续追加.theSection是尝试读取该div节点上名为theSection的属性,但theSection是函数内定义的局部变量,既不是DOM节点的内置属性也不是自定义属性,这一步直接返回undefined,后续访问innerHTML自然报错。
修正代码(严格遵循从按钮出发遍历DOM的要求)
const randomNumberEle = document.getElementById("theRandomNumber"); const prizeButton = document.getElementById("prizeOpenButton") const matchNumberToPrizeSection = function (event) { // 读取span内的目标id值,和dataset.id的字符串类型保持一致 const targetId = randomNumberEle.textContent.trim(); // 从点击按钮开始DOM遍历:按钮 -> 上层simulated RNG容器 -> 上层topOfPage容器 -> 相邻的bottomOfPage奖品容器 const prizeContainer = event.target.parentElement.parentElement.nextElementSibling; let winningSection = null; // 遍历奖品容器下的所有子section,匹配对应data-id for (const section of prizeContainer.children) { if (section.dataset.id === targetId) { winningSection = section; break; } } // 匹配到目标节点后即可执行后续逻辑,比如显示中奖区块 if (winningSection) { winningSection.style.display = 'block'; console.log(winningSection.innerHTML); } } prizeButton.addEventListener("click", matchNumberToPrizeSection);
注:如果需要兼容不支持for-of遍历HTMLCollection的老旧环境,只需要把循环换成普通for循环遍历
prizeContainer.children即可,不需要额外做数组转换。
内容的提问来源于stack exchange,提问作者William S
相关产品推荐
相关产品推荐

