[翻译]High Performance JavaScript(001)



第一章  Loading and Execution  加载和运行

 

    JavaScript performance in the browser is arguably the most important usability issue facing developers. The problem is complex because of the blocking nature of JavaScript, which is to say that nothing else can happen while JavaScript code is being executed. In fact, most browsers use a single process for both user interface (UI) updates and JavaScript execution, so only one can happen at any given moment in time. The longer JavaScript takes to execute, the longer it takes before the browser is free to respond to user input.

    JavaScript在浏览器中的性能,可认为是开发者所要面对的最重要的可用性问题。此问题因JavaScript的阻塞特征而复杂,也就是说,当JavaScript运行时其他的事情不能被浏览器处理。事实上,大多数浏览器使用单进程处理UI更新和JavaScript运行等多个任务,而同一时间只能有一个任务被执行。JavaScript运行了多长时间,那么在浏览器空闲下来响应用户输入之前的等待时间就有多长。
    On a basic level, this means that the very presence of a <script> tag is enough to make the page wait for the script to be parsed and executed. Whether the actual JavaScript code is inline with the tag or included in an external file is irrelevant; the page download and rendering must stop and wait for the script to complete before proceeding. This is a necessary part of the page’s life cycle because the script may cause changes to the page while executing. The typical example is using document.write() in the middle of a page (as often used by advertisements). For example:

    从基本层面说,这意味着<script>标签的出现使整个页面因脚本解析、运行而出现等待。不论实际的JavaScript代码是内联的还是包含在一个不相干的外部文件中,页面下载和解析过程必须停下,等待脚本完成这些处理,然后才能继续。这是页面生命周期必不可少的部分,因为脚本可能在运行过程中修改页面内容。典型的例子是document.write()函数,例如:
<html>
  <head>
    <title>Script Example</title>
  </head>
  <body>
    <p>
      <script type="text/javascript">
        document.write("The date is " + (new Date()).toDateString());
      </script>
    </p>
  </body>
</html>

    When the browser encounters a <script> tag, as in this HTML page, there is no way of knowing whether the JavaScript will insert content into the <p>, introduce additional elements, or perhaps even close the tag. Therefore, the browser stops processing the page as it comes in, executes the JavaScript code, then continues parsing and rendering the page. The same takes place for JavaScript loaded using the src attribute; the browser must first download the code from the external file, which takes time, and then parse and execute the code. Page rendering and user interaction are completely blocked during this time.

    当浏览器遇到一个<script>标签时,正如上面HTML页面中那样,无法预知JavaScript是否在<p>标签中添加内容。因此,浏览器停下来,运行此JavaScript代码,然后再继续解析、翻译页面。同样的事情发生在使用src属性加载JavaScript的过程中。浏览器必须首先下载外部文件的代码,这要占用一些时间,然后解析并运行此代码。此过程中,页面解析和用户交互是被完全阻塞的。


Script Positioning 脚本位置
    The HTML 4 specification indicates that a <script> tag may be placed inside of a <head> or <body> tag in an HTML document and may appear any number of times within each. Traditionally, script> tags that are used to load external JavaScript files have appeared in the <head>, along with <link> tags to load external CSS files and other metainformation about the page. The theory was that it's best to keep as many style and behavior dependencies together, loading them first so that the page will come in looking and behaving correctly. For example:

    HTML 4文档指出,一个<script>标签可以放在HTML文档的<head>或<body>标签中,可以在其中多次出现。传统上,<script>标签用于加载外部JavaScript文件。<head>部分除此类代码外,还包含<link>标签用于加载外部CSS文件和其他页面中间件。也就是说,最好把风格和行为所依赖的部分放在一起,首先加载他们,使得页面可以得到正确的外观和行为。例如:
<html>
  <head>
    <title>Script Example</title>
    <-- Example of inefficient script positioning -->
    <script type="text/javascript" src="file1.js"></script>
    <script type="text/javascript" src="file2.js"></script>
    <script type="text/javascript" src="file3.js"></script>
    <link rel="stylesheet" type="text/css" href="styles.css">
  </head>
  <body>
    <p>Hello world!</p>
  </body>
</html>

    Though this code seems innocuous, it actually has a severe performance issue: there are three JavaScript files being loaded in the <head>. Since each <script> tag blocks the page from continuing to render until it has fully downloaded and executed the JavaScript code, the perceived performance of this page will suffer. Keep in mind that browsers don't start rendering anything on the page until the opening <body> tag is encountered. Putting scripts at the top of the page in this way typically leads to a noticeable delay, often in the form of a blank white page, before the user can even begin reading or otherwise interacting with the page. To get a good understanding of how this occurs, it's useful to look at a waterfall diagram showing when each resource is downloaded. Figure 1-1 shows when each script and the stylesheet file get downloaded as the page is loading.

    虽然这些代码看起来是无害的,但它们确实存在性能问题:在<head>部分加载了三个JavaScript文件。因为每个<script>标签阻塞了页面的解析过程,直到它完整地下载并运行了外部JavaScript代码之后,页面处理才能继续进行。用户必须忍受这种可以察觉的延迟。请记住,浏览器在遇到<body>标签之前,不会渲染页面的任何部分。用这种方法把脚本放在页面的顶端,将导致一个可以察觉的延迟,通常表现为:页面打开时,首先显示为一幅空白的页面,而此时用户即不能阅读,也不能与页面进行交互操作。为了更好地理解此过程,我们使用瀑布图来描绘每个资源的下载过程。图1-1显示出页面加载过程中,每个脚本文件和样式表文件下载的过程。


Figure 1-1. JavaScript code execution blocks other file downloads

图1-1,JavaScript代码运行过程阻塞其他文件下载
    Figure 1-1 shows an interesting pattern. The first JavaScript file begins to download and blocks any of the other files from downloading in the meantime. Further, there is a delay between the time at which file1.js is completely downloaded and the time at which file2.js begins to download. That space is the time it takes for the code contained in file1.js to fully execute. Each file must wait until the previous one has been downloaded and executed before the next download can begin. In the meantime, the user is met with a blank screen as the files are being downloaded one at a time. This is the behavior of most major browsers today.

    图1-1是一个令人感兴趣的模板。第一个JavaScript文件开始下载,并阻塞了其他文件的下载过程。进一步,在file1.js下载完之后和file2.js开始下载之前有一个延时,这是file1.js完全运行所需的时间。每个文件必须等待前一个文件下载完成并运行完之后,才能开始自己的下载过程。当这些文件下载时,用户面对一个空白的屏幕。这就是今天大多数浏览器的行为模式。
    Internet Explorer 8, Firefox 3.5, Safari 4, and Chrome 2 all allow parallel downloads of JavaScript files. This is good news because the <script> tags don’t necessarily block other <script> tags from downloading external resources. Unfortunately, JavaScript downloads still block downloading of other resources, such as images. And even though downloading a script doesn’t block other scripts from downloading, the page must still wait for the JavaScript code to be downloaded and executed before continuing. So while the latest browsers have improved performance by allowing parallel downloads, the problem hasn’t been completely solved. Script blocking still remains a problem.

    Internet Explorer 8, Firefox 3.5, Safari 4, 和Chrome 2允许并行下载JavaScript文件。这个好消息表明,当一个<script>标签正在下载外部资源时,不必阻塞其他<script>标签。不幸的是,JavaScript的下载仍然要阻塞其他资源的下载过程,例如图片。即使脚本之间的下载过程互不阻塞,页面仍旧要等待所有JavaScript代码下载并执行完成之后才能继续。所以,当浏览器通过允许并行下载提高性能之后,该问题并没有完全解决。脚本阻塞仍旧是一个问题。
    Because scripts block downloading of all resource types on the page, it's recommended to place all <script> tags as close to the bottom of the <body> tag as possible so as not to affect the download of the entire page. For example:

    因为脚本阻塞其他页面资源的下载过程,所以推荐的办法是:将所有<script>标签放在尽可能接近<body>标签底部的位置,尽量减少对整个页面下载的影响。例如:
<html>
  <head>
    <title>Script Example</title>
    <link rel="stylesheet" type="text/css" href="styles.css">
  </head>
  <body>
    <p>Hello world!</p>
    <-- Example of recommended script positioning -->
    <script type="text/javascript" src="file1.js"></script>
    <script type="text/javascript" src="file2.js"></script>
    <script type="text/javascript" src="file3.js"></script>

  </body>
</html>

    This code represents the recommended position for <script> tags in an HTML file. Even though the script downloads will block one another, the rest of the page has already been downloaded and displayed to the user so that the entire page isn’t perceived as slow. This is the Yahoo! Exceptional Performance team’s first rule about JavaScript: put scripts at the bottom.

    此代码展示了所推荐的<script>标签在HTML文件中的位置。尽管脚本下载之间互相阻塞,但页面已经下载完成并且显示在用户面前了,进入页面的速度不会显得太慢。这正是“Yahoo! 优越性能小组”关于JavaScript的第一条定律:将脚本放在底部。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值