Javascript 为什么;TypeError:f不是函数;?

Javascript 为什么;TypeError:f不是函数;?,javascript,function,Javascript,Function,下面是一个例子: var f=函数(x){ 警报(x) } (功能(){ f(1) }())在这种情况下,自动插入分号会让您失望,代码会被解释为IIFE: var f = function(x) { alert(x) }(function() { f(1) }()) 这就是为什么没有定义f 因此,经验法则是:不要以(或[开头。这样你就可以安全地省略分号。在你的例子中,f不是一个函数。如果你改变例子,它是: var f = function(x) { alert(x) };

下面是一个例子:

var f=函数(x){
警报(x)
}
(功能(){
f(1)

}())
在这种情况下,自动插入分号会让您失望,代码会被解释为IIFE:

var f = function(x) {
   alert(x)
}(function() {
   f(1)
}())
这就是为什么没有定义
f


因此,经验法则是:不要以
[
开头。这样你就可以安全地省略分号。

在你的例子中,
f
不是一个函数。如果你改变例子,它是:

var f = function(x) {
   alert(x)
};

(function() {
   f(1)
}());
你与之有冲突(或缺乏冲突)

由于ASI规则,如果一行没有以分号结尾,解析器可以合并行。在您的情况下,
var f=function
语句后缺少分号会导致解析器在初始化
f
之前声明并立即调用该函数,并尝试将结果分配给
f

var f = function(x) {
   alert(x)
}(function() {
   f(1)
}())
通过简单地插入分号,您可以强制解析器打断这两条语句,代码的行为与您预期的一样

解析器更喜欢将它们组合在一起,因为它看到一个函数和似乎是参数的东西(由于前面的括号,空格被忽略)。它调用刚刚声明的函数,然后调用
f
,但是
f
尚未初始化,因此不是函数

我在一个旧的web应用程序中遇到了一个特别有趣的例子(在webpack和browserify合并文件之前):我们只是简单地将JS文件按顺序放在一起,大多数都在IIFE模块中。一个脚本的模块后没有以分号结尾,因此在初始化第一个模块时,下一个模块被作为参数传递。很难找到,因为它发生在应用程序的早期,并且是一个缺失的模块


在这种情况下,我们可以通过在连接的文件之间添加注释,在不更改任何外部代码的情况下修复问题,但良好的做法是在代码末尾添加分号和换行符。这样可以避免所有罕见的空白错误。

类似的问题:感谢您的编辑!感谢您的回答!开始一个带括号的行在IIFE中非常常见。我认为在括号和括号之后使用分号可能更好。@我知道,但这是省略分号唯一可能的问题。IIFE可以从附加分号开始:
;(function(){…}())
。谢谢您的回答!