自动分号插入 (ASI),被认为是 JavaScript 中较为有争议的特征。
ASI 的规则是相对简单的:正如 Isaac Schlueter 曾就经描述的那样,一个 \n
字符总是一个语句的结尾(自动加上 ;
),除非下面之一为真,则不加:
- 该语句有一个没有闭合的括号,数组字面量或对象字面量或其他某种方式,不是有效结束一个语句的方式。(比如,以
.
或,
结尾) - 该行是
--
或++
(在这种情况下它将减量/增量的下一个标记) - 它是个
for()
、while()
、do
、if()
或else
,并且没有{
- 下一行以
[
、(
、+
、*
、/
、-
、,
、.
或一些其它在单个表达式中两个标记之间的二元操作符。
在 ASI 的争论中,一般有两大思想流派。第一个是,我们应该忽略 ASI 的存在,总是手动添加分号。理由是比起记住什么时候是否需要分号,把它们加进来更容易一些,并因此降低了引入错误的可能性。
然而,对使用分号的人而言,ASI 机制有时会很棘手。例如:
return
{
name: "ESLint"
};
这个看起来像是个return语句返回一个对象文本。然而,JavaScript 引擎将代码解释成:
return;
{
name: "ESLint";
}
事实上,一个分号插入到 return 语句之后,导致(块中的标签文本)下面的代码不可达。ESLint semi 和 no-unreachable 规则将会避免你的代码出现这种情况。
争论的另一派别说由于分号的自动插入,它们是可选的,不需要手动添加。然而,对不使用分号的人而言,ASI 机制有时也会很棘手。例如,考虑以下代码:
var globalCounter = { }
(function () {
var n = 0
globalCounter.increment = function () {
return ++n
}
})()
在这个例子中,分号不会被插入到第一行末尾,导致一个运行时错误(因为一个空的对象被调用,犹如它是个函数)。ESLint no-unexpected-multiline 规则将会避免你的代码出现这种情况。
因此,最好是知道 ASI 什么时候插入分号,什么时候不插入分号,让 ESLint 帮你的代码避免这些潜在的意外情况。
网友评论