使用JS文件数组生成HTML有序列表时遇标识符重复声明错误
嘿,我来帮你搞定这个问题!你遇到的重复声明错误,根源其实和你写script标签的方式有关,咱们一步步来理清楚:
为什么会出现这个错误?
首先,const声明的变量是不允许在同一个作用域里重复声明的。你说自己没重复声明fruits,那大概率是你的list.js被重复加载了两次——比如浏览器解析页面时,不小心把引入list.js的脚本执行了两遍,第二次执行const fruits = [...]时就触发了语法错误。
而导致重复加载的间接原因,是你错误地在同一个<script>标签里同时用了src属性和内部代码:当浏览器看到带src的script标签时,会直接忽略标签里的所有内部代码,只加载并执行外部的JS文件。如果你的页面逻辑(或者标签写法问题)导致这个脚本被重复解析,就会重复加载list.js,触发错误。
怎么修复?
第一步:拆分script标签
把外部JS引入和你的DOM操作代码分成两个独立的script标签,这样内部的代码才能正常执行,也能避免潜在的重复加载问题:
修改后的HTML代码:
<div id="fruit"> <h3>Displaying Fruits</h3> <!-- 先加载外部的list.js --> <script src="js/list.js"></script> <!-- 再写生成列表的代码 --> <script> var list = document.createElement('ol'); fruits.forEach(function (element){ var li = document.createElement('li'); li.textContent = element; list.appendChild(li); }); var fruit = document.querySelector('#fruit'); fruit.appendChild(list); </script> </div>
第二步:确保list.js只被引入一次
检查你的整个HTML页面,看看有没有其他地方也写了<script src="js/list.js"></script>,如果有,删掉重复的那一行就行。
额外的优化建议
为了避免DOM还没加载完成就执行代码的问题(比如如果把script标签放到页面头部,#fruit元素还没被解析出来,querySelector会返回null),你可以把所有逻辑都放到list.js里,并加上DOM加载完成的监听:
修改后的list.js:
const fruits = ['Apples', 'Oranges', 'Pears', 'Grapes', 'Pineapples', 'Mangos']; // 等页面DOM全部加载完成后再执行代码 document.addEventListener('DOMContentLoaded', function() { const list = document.createElement('ol'); fruits.forEach(fruit => { const li = document.createElement('li'); li.textContent = fruit; list.appendChild(li); }); const fruitContainer = document.querySelector('#fruit'); fruitContainer.appendChild(list); });
然后HTML里只需要简单引入这个JS文件就好:
<div id="fruit"> <h3>Displaying Fruits</h3> <script src="js/list.js"></script> </div>
这样不仅代码更整洁,还能避免各种DOM加载时序的问题~
内容的提问来源于stack exchange,提问作者Muhammad Faiz

