一般而言,JavaScript脚本是建议放在body标签的底部,因为使用script标签加载JS时,会停止加载后面的内容而停下来解析脚本,并对页面进行渲染,使用script属性加载外部脚本也会造成这样的情况,这样的话,如果在head或者是body的前面放入过多的script标签,并且内容很多的时候,会造成页面在解析完所有script标签的内容前,有短暂的时间白屏(整个页面空白),给用户的体验会很差。但是如果所有的脚本都放在底部,又会造成DOM加载完毕后,有一段时间,页面虽然能看到,但是和用户的交互会很差,因此需要让一些脚本与页面,异步加载!
- 在html5中,script新增了async的属性,script添加了该属性之后,下载脚本时将可以与页面其他内容并行下载,但是该属性必须在IE9以上的浏览器中才可以使用,并且只能用于加载外部JS脚本
- 同样在html4中,也有一个defer属性,该属性的交融性更好一点,但是与async一样,可以让js脚本实现异步加载。同样只能用于加载外部脚本。
async与defer属性的不同点是:
async会让脚本在加载完可用时,立即执行,但是derfer脚本则会在DOM加载完毕后执行,defer脚本的执行会在window.onload之前,其他没有添加defer属性的script标签之后
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Document</title>
</head>
<script>
window.onload= function (){
console.log("window.onload");
}
</script>
<script src="defer.js" defer> </script>
<script >
console.log("hello");
</script>
<body>
</body>
</html>
显示顺序为hello , defer, window.onload
- 利用XHR异步加载JS内容并执行,代码如下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Document</title>
</head>
<script>
<script>
var xhr = new XMLHttpRequest() ;
xhr.open("get", "defer.js", true)
xhr.send();
xhr.onreadystatechange = function(){
if(xhr.readystate == 4 && xhr.status == 200){
eval (xhr.responseText);
}
}
</script>
</script>
<body>
</body>
</html>
- 动态创建script标签,代码如下:
<script>
var script = document.createElement("script");
script.src = "defer.js";
document.head.appendchild(script);
</script>
- iframe方式,利用iframe加载一个同源的子页面,让子页面js影响当前父页面的一种方式