JavaScript'的规则是什么;自动分号插入(ASI)?
首先,我应该问一下这是否依赖于浏览器 我已经读到,如果发现一个无效的标记,但代码部分在该无效标记之前是有效的,那么如果标记前面有换行符,则在该标记之前插入一个分号 然而,对于分号插入引起的错误,最常见的例子是:JavaScript'的规则是什么;自动分号插入(ASI)?,javascript,automatic-semicolon-insertion,Javascript,Automatic Semicolon Insertion,首先,我应该问一下这是否依赖于浏览器 我已经读到,如果发现一个无效的标记,但代码部分在该无效标记之前是有效的,那么如果标记前面有换行符,则在该标记之前插入一个分号 然而,对于分号插入引起的错误,最常见的例子是: return _a+b; $('#myButton') .click(function(){alert("Hello!")}); …这似乎不符合这个规则,因为_a是一个有效的代币 另一方面,断开呼叫链的工作与预期一样: return _a+b; $('#myButton
return
_a+b;
$('#myButton')
.click(function(){alert("Hello!")});
…这似乎不符合这个规则,因为_a是一个有效的代币
另一方面,断开呼叫链的工作与预期一样:
return
_a+b;
$('#myButton')
.click(function(){alert("Hello!")});
有人对这些规则有更深入的描述吗?首先,您应该知道哪些语句受自动分号插入(为简洁起见,也称为ASI)的影响:
- 空话
语句var
- 表达式语句
语句do while
语句继续
语句break
语句return
语句throw
- 至少有一个
将令牌与上一个令牌分开LineTerminator
- 令牌是
}
{ 1
;2 ;} 3;
return;
"something";
NumericLiteral
1
满足第一个条件,以下标记是行终止符。2
满足第二个条件,以下标记为}
a = b;
++c;
UpdateExpression :
LeftHandSideExpression [no LineTerminator here] ++
LeftHandSideExpression [no LineTerminator here] --
ContinueStatement :
continue ;
continue [no LineTerminator here] LabelIdentifier ;
BreakStatement :
break ;
break [no LineTerminator here] LabelIdentifier ;
ReturnStatement :
return ;
return [no LineTerminator here] Expression ;
ThrowStatement :
throw [no LineTerminator here] Expression ;
ArrowFunction :
ArrowParameters [no LineTerminator here] => ConciseBody
YieldExpression :
yield [no LineTerminator here] * AssignmentExpression
yield [no LineTerminator here] AssignmentExpression
经典的例子是ReturnStatement
:
return
"something";
转化为
{ 1
;2 ;} 3;
return;
"something";
直截了当地说:
7.9.1自动分号插入规则
分号插入有三个基本规则:
- 至少有一个
将有问题的令牌与前一个令牌分开LineTerminator
- 有问题的标记是}
program
,则会自动在输入流的结尾插入分号LineTerminator
here]”之后的终端或非终端的第一个标记在受限生产内(因此此类令牌称为受限令牌),受限令牌与前一个令牌之间至少有一个行终止符,然后在受限令牌之前自动插入分号关于分号插入和var语句,请注意在使用var但跨越多行时忘记逗号。昨天有人在我的代码中发现:
var srcRecords = src.records
srcIds = [];
它运行了,但效果是srcIds声明/赋值是全局的,因为上一行带有var的局部声明不再应用,因为该语句由于自动插入分号而被视为已完成。我不能太好地理解规范中的这3条规则——希望有更简单的内容英语——但以下是我从JavaScript中收集到的信息:《权威指南》,第6版,大卫·弗拉纳根,O'Reilly,2011年: 引述: JavaScript不会将每一个换行符都视为分号:只有当它无法解析没有分号的代码时,才会将换行符视为分号 另一句话:代码
var a
a
=
3 console.log(a)
JavaScript不会将第二个换行符视为分号,因为它可以继续解析较长的语句a=3
以及:
当JavaScript无法将第二行解析为第一行语句的延续时,它将换行符解释为分号的一般规则有两个例外。第一个异常涉及return、break和continue语句
。。。如果这些单词后面出现换行符。。。JavaScript总是将该换行符解释为分号
。。。第二个异常涉及++和−− 操作员。。。如果要将这些运算符中的任何一个用作后缀运算符,则它们必须与应用于它们的表达式显示在同一行。否则,换行符将被视为分号,并且++或-,将被解析为应用于后面代码的前缀运算符。考虑这个代码,例如:
它被解析为x++y代码>,而不是x++;y
所以我瘦了
return; // returning nothing
{
foo: 1
}
return {
foo: 1
}
return {
foo: 1
};
const foo = function(){ return "foo" } //this doesn't add a semicolon here.
(function (){
console.log("aa");
})()