JavaScript 库中的前导分号有什么作用?

IT技术 javascript syntax
2021-01-15 20:42:25

在几个 JavaScript 库中,我一开始就看到了这个符号:

/**
 * Library XYZ
 */
;(function () {
  // ... and so on

虽然我对“立即执行的函数”语法非常满意

(function(){...})()

我想知道前导分号是做什么用的。我能想到的就是它是一种保险。也就是说,如果该库嵌入到其他有缺陷的代码中,则它充当“最后一条语句最迟在此处结束”的一种减速带。

它还有其他功能吗?

6个回答

它允许您将多个 JavaScript 文件安全地连接为一个,以作为一个 HTTP 请求更快地提供服务。

是的 Boldewyn,但事实并非如此。
2021-03-20 20:42:25
仅仅因为第三个文件包含这个肮脏的修复,两个错误编码的文件将不适合。为什么连接器不能在结果中的文件之间添加额外的分号?
2021-03-20 20:42:25
我的意思是“正确编码”,每个库都以正确数量的尾随分号结尾......
2021-03-25 20:42:25
但是没有必要,如果所有文件都正确编码,是吗?
2021-03-27 20:42:25
否:在您的示例中,您会得到(function(){...})()(function(){...})().
2021-04-05 20:42:25

最佳答案实际上是在问题中给出的,所以为了清楚起见,我将在这里写下来:

;立即调用的函数表达式前面的前导是为了防止在连接期间将文件附加到包含未正确终止的表达式的文件时出错;

最佳做法是用分号终止表达式,但也使用前导分号作为保护措施。

因为你不能按照你的约定依赖别人的代码。防御性地编码,然后你就不必了。
2021-03-18 20:42:25
如果您使用防御性分号,为什么还要用分号终止您的表达式?要么抓住机会在每行末尾使用分号,要么使用防御性分号。两者都做会使人们错误地得出结论,认为两者都做是有原因的。使用防御性分号的建议很好;建议也替换"\n"with 的每个实例是";\n"没有意义的。
2021-03-30 20:42:25
@VladimirKornea:因为您并不总是只使用自己的库:)
2021-03-30 20:42:25
@VladimirKornea 如果您愿意,您也可以将其视为防御性的 - 它可以防御其他人的代码,这些代码并不总是以防御性分号开头。
2021-04-09 20:42:25

一般来说,如果一个语句以 (, [, /, +, or - 开头,那么它就有可能被解释为之前语句的延续。以 /, +, 和 - 开头的语句在实践中是很少见的, 但是以 ( 和 [ 开头的语句并不少见, 至少在某些 JavaScript 编程风格中是这样。一些程序员喜欢在任何此类语句的开头放置一个防御分号, 以便即使语句在它被修改并删除之前终止的分号之前:

var x = 0 // Semicolon omitted here
;[x,x+1,x+2].forEach(console.log) // Defensive ; keeps this statement separate

来源:

JavaScript:权威指南,第 6 版

这称为前导分号。

它的主要目的是保护自己免受先前未正确关闭的代码的影响,这可能会导致问题。分号可以防止这种情况发生。如果前面的代码没有正确关闭,那么我们的分号会纠正这个问题。如果它被正确关闭,那么我们的分号将是无害的,也不会产生副作用。

一个单行的答案是安全地连接多个 JavaScript 文件。使用分号不会引起问题。

假设你有多个函数:

IFE 1

(function(){
  // The rest of the code
})(); // Note it is an IIFE

IIFE 2

(function(){
   // The rest of the code
})(); // Note it is also an IIFE

在串联时,它可能看起来像:

(function(){})()(function(){})()

但是如果在函数前添加分号,它将如下所示:

;(function(){})();(function(){})()

因此,通过添加 a ;,它会注意是否有任何表达式未正确终止。

示例 2

假设您有一个带有变量的 JavaScript 文件:

var someVar = "myVar"

另一个具有某些功能的 JavaScript 文件:

(function(){})()

现在在串联它看起来像

var someVar = "myVar"(function(){})() // It may give rise to an error

使用分号,它看起来像:

var someVar = "myVar";(function(){})()