2019-04-21 11:50:48 +08:00

165 lines
13 KiB
HTML
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<article id="wikiArticle">
<div>
<div></div>
</div>
<p><strong>块语句</strong>(或其他语言的<strong>复合语句</strong>)用于组合零个或多个语句。该块由一对大括号界定,可以是<a href="Reference/Statements/label" title="标记语句可以和 break 或 continue 语句一起使用。标记就是在一条语句前面加个可以引用的标识符。"><code>labelled</code></a></p>
<h2 id="语法">语法</h2>
<h3 id="块声明">块声明</h3>
<pre><code class="language-javascript">{ <em>StatementList </em>}
</code></pre>
<h3 id="标记块声明">标记块声明</h3>
<pre><code class="language-javascript"><em>LabelIdentifier</em>: { <em>StatementList </em>}
</code></pre>
<dl>
<dt><code>StatementList</code></dt>
<dd>在块语句中分组的语句。</dd>
<dt><code>LabelIdentifier</code></dt>
<dd>用于视觉识别的可选<a href="Reference/Statements/label" title="标记语句可以和 break 或 continue 语句一起使用。标记就是在一条语句前面加个可以引用的标识符。"><code>label</code></a><a href="Reference/Statements/break" title="break 语句中止当前循环switch语句或label 语句,并把程序控制流转到紧接着被中止语句后面的语句。"><code>break</code></a>的目标。</dd>
</dl>
<h2 id="描述">描述</h2>
<p>其他语言中通常将语句块称为<strong>复合语句</strong>。它允许你使用多个语句,其中 JavaScript 只需要一个语句。将语句组合成块是 JavaScript 中的常见做法。相反的做法是可以使用一个<a href="Reference/Statements/Empty">空语句</a>,你不提供任何语句,虽然一个是必需的。</p>
<h3 id="块级作用域">块级作用域</h3>
<h4 id="使用var">使用<code>var</code></h4>
<p>通过<code>var</code>声明的变量<strong>没有</strong>块级作用域。在语句块里声明的变量作用域是其所在的函数或者 script 标签内,你可以在语句块外面访问到它。换句话说,语句块 不会生成一个新的作用域。尽管单独的语句块是合法的语句但在JavaScript中你不会想使用单独的语句块因为它们不像你想象的C或Java中的语句块那样处理事物。例如</p>
<pre><code class="language-js example-bad">var x = 1;
{
var x = 2;
}
console.log(x); // 输出 2
</code></pre>
<p>该会输出2因为块中的 <code>var x</code>语句与块前面的<code>var x</code>语句作用域相同。在 C 或 Java中这段代码会输出 1。</p>
<h4 id="使用let和_const">使用<code>let</code><code>const</code></h4>
<p>相比之下,使用 <a href="Reference/Statements/let" title="let允许你声明一个作用域被限制在块级中的变量、语句或者表达式。与var关键字不同的是var声明的变量只能是全局或者整个函数块的。"><code>let</code></a><a href="Reference/Statements/const" title="常量是块级作用域,很像使用 let 语句定义的变量。常量的值不能通过重新赋值来改变并且不能重新声明。"><code>const</code></a>声明的变量是<strong></strong>块级作用域的。</p>
<pre><code class="language-javascript">let x = 1;
{
let x = 2;
}
console.log(x); // 输出 1</code></pre>
<p><code>x = 2</code>被限制在块级作用域中, 也就是它被声明时所在的块级作用域。</p>
<p><code>const</code>的结果也是一样的:</p>
<pre><code class="language-javascript">const c = 1;
{
const c = 2;
}
console.log(c); // 输出1, 而且不会报错</code></pre>
<p>注意块级作用域里的常量声明<code>const c = 2</code> 并不会抛出<code>SyntaxError: Identifier 'c' has already been declared</code>这样的语法错误,因为这是一个新的作用域。</p>
<h5 id="使用let声明的变量在块级作用域内能强制执行更新变量下面的两个例子对比">使用let声明的变量在块级作用域内能强制执行更新变量下面的两个例子对比</h5>
<pre><code class="language-javascript">var a = [];
for (<strong>var</strong> i = 0; i &lt; 10; i++) {
a[i] = function () {console.log(i);};
}
a[0](); // 10
a[1](); // 10
a[6](); // 10
/********************/
var a = [];
for (<strong>let</strong> i = 0; i &lt; 10; i++) {
a[i] = function () {console.log(i);};
}
a[0](); // 0
a[1](); // 1
a[6](); // 6</code></pre>
<h4 id="使用function">使用<code>function</code></h4>
<p><a href="https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/function">函数声明</a>同样被限制在声明他的语句块内:</p>
<p> </p>
<pre><code>foo('outside'); // TypeError: foo is not a function
{
function foo(location) {
console.log('foo is called ' + location);
}
foo('inside'); // 正常工作并且打印 'foo is called inside'
}</code></code></pre>
<p> </p>
<h2 id="规范">规范</h2>
<table class="standard-table">
<tbody>
<tr>
<th scope="col">Specification</th>
<th scope="col">Status</th>
<th scope="col">Comment</th>
</tr>
<tr>
<td><a class="external" href="https://tc39.github.io/ecma262/#sec-block" hreflang="en" lang="en" rel="noopener">ECMAScript Latest Draft (ECMA-262)<br/><small lang="zh-CN">Block statement</small></a></td>
<td><span class="spec-Draft">Draft</span></td>
<td> </td>
</tr>
<tr>
<td><a class="external" href="https://www.ecma-international.org/ecma-262/6.0/#sec-block" hreflang="en" lang="en" rel="noopener">ECMAScript 2015 (6th Edition, ECMA-262)<br/><small lang="zh-CN">Block statement</small></a></td>
<td><span class="spec-Standard">Standard</span></td>
<td> </td>
</tr>
<tr>
<td><a class="external" href="https://www.ecma-international.org/ecma-262/5.1/#sec-12.1" hreflang="en" lang="en" rel="noopener">ECMAScript 5.1 (ECMA-262)<br/><small lang="zh-CN">Block statement</small></a></td>
<td><span class="spec-Standard">Standard</span></td>
<td> </td>
</tr>
<tr>
<td><a class="external" href="https://www.ecma-international.org/publications/files/ECMA-ST-ARCH/ECMA-262,%203rd%20edition,%20December%201999.pdf#sec-12.1" hreflang="en" lang="en" rel="noopener">ECMAScript 3rd Edition (ECMA-262)<br/><small lang="zh-CN">Block statement</small></a></td>
<td><span class="spec-Standard">Standard</span></td>
<td> </td>
</tr>
<tr>
<td><a class="external" href="https://www.ecma-international.org/publications/files/ECMA-ST-ARCH/ECMA-262,%201st%20edition,%20June%201997.pdf#sec-12.1" hreflang="en" lang="en" rel="noopener">ECMAScript 1st Edition (ECMA-262)<br/><small lang="zh-CN">Block statement</small></a></td>
<td><span class="spec-Standard">Standard</span></td>
<td>Initial definition. Implemented in JavaScript 1.0.</td>
</tr>
</tbody>
</table>
<h2 id="浏览器兼容">浏览器兼容</h2>
<div class="hidden">The compatibility table on this page is generated from structured data. If you'd like to contribute to the data, please check out <a class="external" href="https://github.com/mdn/browser-compat-data" rel="noopener">https://github.com/mdn/browser-compat-data</a> and send us a pull request.</div>
<p></p><div class="bc-data"><a class="bc-github-link external" href="https://github.com/mdn/browser-compat-data" rel="noopener">Update compatibility data on GitHub</a><table class="bc-table bc-table-js"><thead><tr class="bc-platforms"><td></td><th class="bc-platform-desktop" colspan="6"><span>Desktop</span></th><th class="bc-platform-mobile" colspan="7"><span>Mobile</span></th><th class="bc-platform-server" colspan="1"><span>Server</span></th></tr><tr class="bc-browsers"><td></td><th class="bc-browser-chrome"><span class="bc-head-txt-label bc-head-icon-chrome">Chrome</span></th><th class="bc-browser-edge"><span class="bc-head-txt-label bc-head-icon-edge">Edge</span></th><th class="bc-browser-firefox"><span class="bc-head-txt-label bc-head-icon-firefox">Firefox</span></th><th class="bc-browser-ie"><span class="bc-head-txt-label bc-head-icon-ie">Internet Explorer</span></th><th class="bc-browser-opera"><span class="bc-head-txt-label bc-head-icon-opera">Opera</span></th><th class="bc-browser-safari"><span class="bc-head-txt-label bc-head-icon-safari">Safari</span></th><th class="bc-browser-webview_android"><span class="bc-head-txt-label bc-head-icon-webview_android">Android webview</span></th><th class="bc-browser-chrome_android"><span class="bc-head-txt-label bc-head-icon-chrome_android">Chrome for Android</span></th><th class="bc-browser-edge_mobile"><span class="bc-head-txt-label bc-head-icon-edge_mobile">Edge Mobile</span></th><th class="bc-browser-firefox_android"><span class="bc-head-txt-label bc-head-icon-firefox_android">Firefox for Android</span></th><th class="bc-browser-opera_android"><span class="bc-head-txt-label bc-head-icon-opera_android">Opera for Android</span></th><th class="bc-browser-safari_ios"><span class="bc-head-txt-label bc-head-icon-safari_ios">Safari on iOS</span></th><th class="bc-browser-samsunginternet_android"><span class="bc-head-txt-label bc-head-icon-samsunginternet_android">Samsung Internet</span></th><th class="bc-browser-nodejs"><span class="bc-head-txt-label bc-head-icon-nodejs">Node.js</span></th></tr></thead><tbody><tr><th scope="row"><code>block</code></th><td class="bc-supports-yes bc-browser-chrome"><span class="bc-browser-name">Chrome</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
Yes</td><td class="bc-supports-yes bc-browser-edge"><span class="bc-browser-name">Edge</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
Yes</td><td class="bc-supports-yes bc-browser-firefox"><span class="bc-browser-name">Firefox</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
1</td><td class="bc-supports-yes bc-browser-ie"><span class="bc-browser-name">IE</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
Yes</td><td class="bc-supports-yes bc-browser-opera"><span class="bc-browser-name">Opera</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
Yes</td><td class="bc-supports-yes bc-browser-safari"><span class="bc-browser-name">Safari</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
Yes</td><td class="bc-supports-yes bc-browser-webview_android"><span class="bc-browser-name">WebView Android</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
Yes</td><td class="bc-supports-yes bc-browser-chrome_android"><span class="bc-browser-name">Chrome Android</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
Yes</td><td class="bc-supports-yes bc-browser-edge_mobile"><span class="bc-browser-name">Edge Mobile</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
Yes</td><td class="bc-supports-yes bc-browser-firefox_android"><span class="bc-browser-name">Firefox Android</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
4</td><td class="bc-supports-yes bc-browser-opera_android"><span class="bc-browser-name">Opera Android</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
Yes</td><td class="bc-supports-yes bc-browser-safari_ios"><span class="bc-browser-name">Safari iOS</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
Yes</td><td class="bc-supports-yes bc-browser-samsunginternet_android"><span class="bc-browser-name">Samsung Internet Android</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
Yes</td><td class="bc-supports-yes bc-browser-nodejs"><span class="bc-browser-name">nodejs</span><abbr class="bc-level-yes only-icon" title="Full support">
<span>Full support</span>
</abbr>
Yes</td></tr></tbody></table><section class="bc-legend" id="sect1"><h3 class="offscreen" id="Legend">Legend</h3><dl><dt><span class="bc-supports-yes bc-supports">
<abbr class="bc-level bc-level-yes only-icon" title="Full support">
<span>Full support</span>
 
</abbr></span></dt><dd>Full support</dd></dl></section></div><p></p>
<h2 id="See_also" name="See_also">相关链接</h2>
<ul>
<li><a href="Reference/Statements/while" title="while 语句可以在某个条件表达式为真的前提下,循环执行指定的一段代码,直到那个表达式不为真时结束循环。"><code>while</code></a></li>
<li><a href="Reference/Statements/if...else" title="当指定条件为真if 语句会执行一段语句。如果条件为假,则执行另一段语句。"><code>if...else</code></a></li>
<li><a href="Reference/Statements/let" title="let允许你声明一个作用域被限制在块级中的变量、语句或者表达式。与var关键字不同的是var声明的变量只能是全局或者整个函数块的。"><code>let</code></a></li>
</ul>
</article>