Javascript在页面加载时的执行顺序(转载)

原文:http://dancewithnet.com/2007/03/22/order-of-execution-of-javascript-on-web/

一、在HTML中嵌入Javasript的方法

  1. 直接在Javascript代码放在标记对<script>和</script>之间
  2. 由<script />标记的src属性制定外部的js文件
  3. 放在事件处理程序中,比如:<p onclick="alert('我是由onclick事件执行的Javascript')">点击我</p>
  4. 作为URL的主体,这个URL使用特殊的Javascript:协议,比如:<a href="javascript:alert('我是由javascript:协议执行的javascript')">点击我</a>
  5. 利用javascript本身的document.write()方法写入新的javascript代码
  6. 利用Ajax异步获取javascript代码,然后执行

第3种和第4种方法写入的Javascript需要触发才能执行,所以除非特别设置,否则页面加载时不会执行。

二、Javascript在页面的执行顺序

  1. 页面上的Javascript代码是HTML文档的一部分,所以Javascript在页面装载时执行的顺序就是其引入标记<script />的出现顺序, <script />标记里面的或者通过src引入的外部JS,都是按照其语句出现的顺序执行,而且执行过程是文档装载的一部分。
  2. 每个脚本定义的全局变量和函数,都可以被后面执行的脚本所调用。
  3. 变量的调用,必须是前面已经声明,否则获取的变量值是undefined。
    <script type="text/javscrpt">//<![CDATA[
    alert(tmp);  //输出 undefined
    var tmp = 1;
    alert(tmp);  //输出 1
    //]]></script>
  4. 同一段脚本,函数定义可以出现在函数调用的后面,但是如果是分别在两段代码,且函数调用在第一段代码中,则会报函数未定义错误。
    <script type="text/javscrpt">//<![CDATA[
    aa();            //浏览器报错
    //]]></script>
    <script type="text/javscrpt">//<![CDATA[
    aa();            //输出 1 
    function aa(){alert(1);}
    //]]></script>
  5. document.write()会把输出写入到脚本文档所在的位置,浏览器解析完documemt.write()所在文档内容后,继续解析document.write()输出的内容,然后在继续解析HTML文档。
    <script type="text/javascript">//<![CDATA[document.write('<script type="text/javascript" src="test.js"><\/script>');document.write('<script type="text/javascript">');document.write('alert(2);')document.write('alert("我是" + tmpStr);');document.write('<\/script>');//]]></script><script type="text/javascript">//<![CDATA[alert(3);//]]></script>

    test.js的内容是:

    var tmpStr = 1;
    alert(tmpStr);
    • 在Firefox和Opera中的弹出值的顺序是:1、2、我是1、3
    • 在IE中弹出值的顺序是:2、1、3,同时浏览器报错:tmpStr未定义

    原因可能是IE在document.write时,并未等待加载SRC中的Javascript代码完毕后,才执行下一行,所以导致2先弹出,并且 执行到document.write(‘document.write("我是" + tmpStr)’)调用tmpStr时,tmpStr并未定义,从而报错。

    解决这个问题,可以利用HTML解析是解析完一个HTML标签,再执行下一个的原理,把代码拆分来实现:

    <script type="text/javascript">//<![CDATA[document.write('<script type="text/javascript" src="test.js"><\/script>');//]]></script><script type="text/javascript">//<![CDATA[document.write('<script type="text/javascript">');document.write('alert(2);')document.write('alert("我是" + tmpStr);');document.write('<\/script>');//]]></script><script type="text/javascript">//<![CDATA[alert(3);//]]></script>

    这样IE下和其他浏览器输出值的顺序都是一直的了:1、2、我是1、3。

三、如何改变Javascript在页面的执行顺序

    1. 利用onload
      <script type="text/javascript">//<![CDATA[
      window.onload = f;
      function f(){alert(1);}
      alert(2);
      //]]></script>

      输出值顺序是 2、1。

      需要注意的是,如果存在多个winodws.onload的话,只有最有一个生效,解决这个办法是:

      window.onload = function(){f();f1();f2();.....}
      利用2级DOM事件类型
      if(document.addEventListener){
      window.addEventListener('load',f,false);
      window.addEventListener('load',f1,false);
      ...
      }else{
      window.attachEvent('onload',f);
      window.attachEvent('onload',f1);
      ...
      }
    2. IE中可以利用defer,defer作用是把代码加载下来,并不立即执行,等文档装载完毕之后再执行,有点类似window.onload,但是没有window.onload那样的局限性,可以重复使用,但是只在IE中有效,所以上面的例子可以修改成为
      <script type="text/javascript">//<![CDATA[
      document.write('<script type="text/javascript" src="test.js"><\/script>');
      document.write('<script type="text/javascript" defer="defer">');
      document.write('alert(2);')
      document.write('alert("我是" + tmpStr);');
      document.write('<\/script>');
      //]]></script>
      <script type="text/javascript">//<![CDATA[
      alert(3);
      //]]></script>

      这样IE就不报错了,输出值的顺序变成:1、3、2、我是1

      当HTML解析器遇到一个脚本,它必须按常规终止对文档的 解析并等待脚本执行。为了解决这个问题HTML4标准定义了defer。通过defer来提示浏览器可以继续解析HTML文档,并延迟执行脚本。这种延迟 在脚本从外部文件载入时非常有用,让浏览器不必等待外部文件全部载入之后才继续执行,能有效的提高性能。IE是目前唯一支持defer属性的浏览器,但 IE并没有正确的实现了defer属性,因为延迟的脚本总是被延迟,直到文档结束,而不是只延迟到下一个非延迟的脚本。这意味着,IE中延迟的脚本的执行 顺序相当混乱,并且不能定义任何后面非延迟脚本并须的函数和变量。在IE中所有的defer的脚本执行时间应该都是HTML文档树建立以 后,window.onload之前。
    3. 利用Ajax。
      因为xmlhttpRequest能判断外部文档加载的状态,所以能够改变代码的加载顺序。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/276197.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

TClientDataSet[27]: 字段值的约束(或叫输入限制)

Required、Precision、MaxValue、MinValue:begin{ Required: 必填字段 }with TIntegerField.Create(Self) do beginFieldName : ID;Required : True;DataSet : ClientDataSet1;end;{ Precision: 浮点数精度}with TFloatField.Create(Self) do beginFieldName : Float;Precision…

年度总结文章的抽奖结果公布

大家好&#xff0c;我是若川。2月4日&#xff0c;发表了我的2020年度总结文章《若川的2020年度总结&#xff0c;水波不兴》&#xff0c;本以为阅读量应该突破一千会比较快&#xff0c;实际上比较艰难&#xff0c;而且还掉粉10来人。2020年运营公众号以来&#xff0c;不知不觉发…

php 正则表达式 匹配中日韩字符(GBK)

转载链接&#xff1a;http://www.cnblogs.com/ITEagle/archive/2013/01/14/2859775.html 首先是这些非英文字符的编码范围&#xff1a; 这里是几个主要非英文语系字符范围 2E80&#xff5e;33FFh&#xff1a;中日韩符号区。收容康熙字典部首、中日韩辅助部首、注音符号、日本假…

linux多线程求和_linux 多线程信号处理总结

linux 多线程信号总结(一)1. 在多线程环境下&#xff0c;产生的信号是传递给整个进程的&#xff0c;一般而言&#xff0c;所有线程都有机会收到这个信号&#xff0c;进程在收到信号的的线程上下文执行信号处理函数&#xff0c;具体是哪个线程执行的难以获知。也就是说&#xff…

Elon Musk

人物事件 成长学习 1971年6月28日&#xff0c;埃隆马斯克在南非的比勒陀利亚出生&#xff0c;他的 埃隆马斯克 父亲是一名南非机电工程师&#xff0c;母亲是加拿大人&#xff0c;从事营养师兼模特。[8] 1981年&#xff0c;10岁的马斯克就拥有了自己的第一台电脑&#xff0c;并…

真诚推荐这7个大佬的公众号,碎片化学习

逆水行舟&#xff0c;不进则退。我们的工作已经占用了大块的时间了&#xff0c;剩下的只有各种碎片&#xff0c;最适合碎片时间学习的&#xff0c;莫过于优质的技术干货公众号啦~以下这些是小编精选&#xff0c;里面有很多资讯和资源&#xff0c;内含干货&#xff0c;希望能给大…

[转]Windows 7 产品密钥是否安全

提到Windows 7&#xff08;或Windows Server 2008&#xff09;有些人认为自己的产品密钥&#xff08;Product Key&#xff09;很安全&#xff0c;甚至在公司内部有些网管也认为公司部署的Windows 7 系统的密钥不会泄露。但其实并非如此&#xff0c;众所周知我们的密钥都是写在注…

HttpWatch的Result中出现Aborted的原因分析[配图]

转载链接&#xff1a;http://www.cnblogs.com/yutiansanshou/archive/2013/02/01/2889486.html 我们在使用HttpWatch进行Web调试的过程中有时候会看到非HTTP Status Code&#xff08;状态码&#xff09;的值&#xff0c; 例如&#xff1a;(Aborted)。 (Aborted)是HttpWatch中定…

android显示布局边界的边距_Android设计规范 Material Design-Layout(2 度量与边框)

度量与边框基准网络所有组件都与间隔为8dp的基准网格对齐。排版/文字(Type)与间隔为4dp的基准网格对齐。在工具条中的图标同样与间隔为4dp的基准网格对齐。这些规则适用于移动设备、平板设备以及桌面应用程序。有关详细信息请参见组件一节。有关详细信息请参见字体排版一节。边…

《大规模分布式系统架构与设计实战》

《大规模分布式系统架构与设计实战》 基本信息 作者&#xff1a; 彭渊 丛书名&#xff1a; 大数据技术丛书 出版社&#xff1a;机械工业出版社 ISBN&#xff1a;9787111455035 上架时间&#xff1a;2014-2-21 出版日期&#xff1a;2014 年2月 开本&#xff1a;16开 页码&…

WINDOWS下的squid

今天写这篇教程目的在于分享自己在WINDOWS主机下配置squid的方法。哪些地方写的不完善或是不完整或是需要修改的地方&#xff0c;大家可以提出。我会第一时间纠正。下面看正文部分。先提条件&#xff0c;您预安装配置squid的这台计算机必须是联入网络的&#xff0c;系统版本是w…

Provide/inject 真的可以取代 Vuex 吗?

Hello&#xff0c;各位小伙伴&#xff0c;接下来的一段时间里&#xff0c;我会把我的课程《Vue.js 3.0 核心源码解析》中问题的答案陆续在我的公众号发布&#xff0c;由于课程的问题大多数都是开放性的问题&#xff0c;所以我的答案也不一定是标准的&#xff0c;仅供你参考喔。…

php 计算代码执行时间

转载链接&#xff1a;http://blog.csdn.net/php_boy/article/details/6450678 class runtime {var $StartTime 0;var $StopTime 0;function get_microtime(){list($usec, $sec) explode( , microtime());return ((float)$usec (float)$sec);}function start(){$this->S…

参数方程求二阶偏导_偏微分方程

常微分方程&#xff08;ODE&#xff09; 的时候我们更多是关于时间的导数。偏微分方程&#xff08;partial differential equation) 则不仅仅是与时间相关&#xff0c;加上了与空间位置相关的一些信息。解当 ODE 满足 利普希茨连续&#xff08;Lipschitz continuity&#xff09…

Spring Batch 批量处理策略

为了帮助设计和实现批量处理系统&#xff0c;基本的批量应用是通过块和模式来构建的&#xff0c;同时也应该能够为程序开发人员和设计人员提供结构的样例和基础的批量处理程序。当你开始设计一个批量作业任务的时候&#xff0c;商业逻辑应该被拆分一系列的步骤&#xff0c;而这…

CString原理介绍

看了很多人写的程序,包括我自己写的一些代码&#xff0c;发现很大的一部分bug是关于MFC类中的CString的错误用法的.出现这种错误的原因主要是对CString的实现机制不是太了解。 CString是对于原来标准c中字符串类型的一种的包装。因为&#xff0c;通过很长时间的编程&#xff0c…

如何从零开始开发一个 Chrome 插件?

什么是浏览器插件&#xff1f;简单来说浏览器插件&#xff0c;是浏览器上的一种工具&#xff0c;可以提供一些浏览器没有的功能&#xff0c;帮你做一些有趣的事情。开发者可以根据自己的喜欢&#xff0c;去实现一些功能。插件基于Web技术&#xff08;html、css、js&#xff09;…

mysql 重复字段查询及排除重复值

转载链接&#xff1a;http://blog.sina.com.cn/s/blog_3edc5e2e010131ys.html mysql 重复字段查询及排除重复值 SELECT a.id,a.title FROM dede_archives a left join dede_taglist t on t.taga.title WHERE t.typeid$id and t.arcrank>-1 and a.typeid28 group by t.tag; …

swiper移入暂停_react中swiper注意事项及鼠标划入停止轮播

首先是实例化swiper这里有一个注意点&#xff0c;就是实例化的时机如果你的swiper内容是写死的&#xff0c;可以在componentDidMount中实例化&#xff0c;但是如果你的内容是通过接口异步请求过来的&#xff0c;就必须在componentDidUpdate里实例化&#xff0c;因为如果在 comp…

轉Excel的一種簡單方法

写了这么久的程序﹐越来越喜欢那种简单的解决方法﹐这段时间在做一个报表系统﹐其中有需要转Excel﹐而且要求兼容openoffice﹐遂利用asp语法,asp.net的控件封装特性以及excel 2003的xml试算清格式做了一个看起来比较"清爽"的excel转档方案。一.开始原理很简单﹐excel…