脚本调用:
最常见的问题就是:HTML 元素是按其在页面中出现的次序调用的,如果用 JavaScript 来管理页面上的元素,若 JavaScript 加载于想操作的 HTML 元素之前,则代码将出错。
JavaScript 在文档头部,解析 HTML 文档体之前加载并执行。这样做是有隐患的,需要使用一些结构来避免错误发生。
1.内部JavaScript,使用了以下结构:
document.addEventListener("DOMContentLoaded", () => {
// …
});
这是一个事件监听器,它监听浏览器的 DOMContentLoaded 事件,其标志了 HTML 文档体完全加载和解析。该代码块中的 JavaScript 在事件被触发后才会运行,因此避免了错误。
2.外部JavaScript,使用了 JavaScript 的一项现代技术(defer 属性)来解决这一问题,它告知浏览器在遇到 <script> 元素时继续下载 HTML 内容。
<script src="script.js" defer></script>
上述情况下,脚本和 HTML 将一并加载,代码将顺利运行。
解决此问题的旧方法是:把脚本元素放在文档体的底端(也就是 </body> 标签之前,与之相邻),这样脚本就可以在 HTML 解析完毕后加载了。此方案的问题是:只有在所有 HTML DOM 加载完成后才开始脚本的加载/解析过程。对于有大量 JavaScript 代码的大型网站,可能会带来显著的性能损耗。
即:

src里面存放的js文件路径(相对于html文件存在的路径)
async 和 defer:
1.功能:
解决脚本阻塞问题。
2.介绍:
async:浏览器遇到 async 脚本时不会阻塞页面渲染,而是直接下载然后运行。但是,一旦下载完成,脚本就会执行,从而阻止页面渲染。脚本的运行次序无法控制。当页面的脚本之间彼此独立,且不依赖于本页面的其他任何脚本时,async 是最理想的选择。
defer:使用 defer 属性加载的脚本将按照它们在页面上出现的顺序加载。在页面内容全部加载完毕之前,脚本不会运行,如果脚本依赖于 DOM 的存在(例如,脚本修改了页面上的一个或多个元素),这一点非常有用。
3.例子:
比如,如果你的页面要加载以下三个脚本:
<script async src="js/vendor/jquery.js"></script>
<script async src="js/script2.js"></script>
<script async src="js/script3.js"></script>
三者的调用顺序是不确定的。jquery.js 可能在 script2 和 script3 之前或之后调用,如果这样,后两个脚本中依赖 jquery 的函数将产生错误,因为脚本运行时 jquery 尚未加载。
async 应该在有大量后台脚本需要加载,并且只想尽快加载到位的情况下使用。
解决这一问题可使用 defer 属性,脚本将按照在页面中出现的顺序加载和运行:
<script defer src="js/vendor/jquery.js"></script>
<script defer src="js/script2.js"></script>
<script defer src="js/script3.js"></script>
添加 defer 属性的脚本将按照在页面中出现的顺序加载,因此第二个示例可确保 jquery.js 必定加载于 script2.js 和 script3.js 之前,同时 script2.js 必定加载于 script3.js 之前。在页面内容全部加载完成之前,它们不会运行。
小结:
async和defer都指示浏览器在一个单独的线程中下载脚本,而页面的其他部分(DOM 等)正在下载,因此在获取过程中页面加载不会被阻塞。async属性的脚本将在下载完成后立即执行。这将阻塞页面,并不保证任何特定的执行顺序。- 带有
defer属性的脚本将按照它们的顺序加载,并且只有在所有脚本加载完毕后才会执行。 - 如果脚本无需等待页面解析,且无依赖独立运行,那么应使用
async。 - 如果脚本需要等待页面解析,且依赖于其他脚本,调用这些脚本时应使用
defer,将关联的脚本按所需顺序置于 HTML 的相应<script>元素中。
本文讲述了JavaScript在页面加载中的常见问题,如何通过DOMContentLoaded事件和使用defer和async属性来避免脚本错误。介绍了这两种方法的工作原理以及何时选择async或defer以确保正确和高效的脚本执行顺序。
4829

被折叠的 条评论
为什么被折叠?



