0

我的问题基本上是对这个问题的扩展: var functionName = function() {} vs function functionName() {}。我已经阅读了所有答案,但我认为我仍然错过了这个问题的答案:

为什么函数声明的类型对于 jQuery 的 onComplete 事件和原生 setInterval 方法很重要?此外,为什么对这些很重要,而对普通的 addEventListener 却没有?

带有 onComplete 事件的示例(假设blinkOn()被调用):

//like this the onComplete event works normally and the functions call eachother
function blinkOn() { $blink.fadeIn( 500, blinkOff ); }
function blinkOff() { $blink.fadeOut( 500, blinkOn ); }

//like this blinkOff won't be called after the fadeIn
function blinkOn() { $blink.fadeIn( 500, blinkOff ); }
var blinkOff = function() { $blink.fadeOut( 500, blinkOn ); };

使用 setInterval 的示例:

//works fine
var timer = setInterval( onTimer, 700);
function onTimer() { ... }

//won't work
var timer = setInterval( onTimer, 700);
var onTimer = function() { ... }

我想知道的原因是因为我希望我的代码保持一致。如果获得它的唯一方法就是使用function a() { ... },那没关系。但我认为var a = function() { ... }在定义范围时更清楚。我真的很好奇。

4

3 回答 3

2

如果您要在调用函数的位置上方定义函数,则不会有任何问题。

var toggleLight = function () { light = !light; };

setInterval(toggleLight, 500);

您的问题是您正在尝试访问尚不存在的东西。

这与尝试执行此操作完全相同:

var c = a + b,

    a = 12,
    b = 3;

当程序命中c时,ab存在。

对于每个单独的功能,可以将其想象为分三个步骤进行:

var a = 12,
    b = 3,
    c = add(a, b);

function add (a, b) { return a + b; }

步骤 1.
引擎获取命名函数add并计算出它的作用(首先定义所有命名函数)。

步骤 2.
引擎定位函数中的所有变量并将它们设置为undefined

var a = undefined,
    b = undefined,
    c = undefined;

function add(a, b) { return a + b; }

STEP 3.
引擎按顺序初始化所有变量。

// 3.1
var a = 12,
    b = undefined,
    c = undefined;


// 3.2
var a = 12,
    b = 3,
    c = undefined;

// 3.3
var a = 12,
    b = 3,
    c = add(a, b); // = return a + b = 15

所以做这样的事情:

callFunction(myFunc);
var myFunc = function () {};

等于:

var myFunc = undefined;
callFunction(myFunc);
myFunc = function () {};

解决方案:

将您的实施与您的行动分开。在调用任何内容之前,请确保所有内容都已定义。

于 2012-10-02T16:41:37.217 回答
1

命名函数是在任何地方创建的,因此它们在定义它们的范围内变得全局可用,因为分配给标识符的匿名函数只有在定义了它们绑定到的标识符后才可用。

所以你遇到的是一个简单的竞争条件问题。如果在变量定义blinkOn()之后调用,您的第一个非工作示例应该可以工作。blikOff

您的第二个非工作示例不起作用,因为在调用时尚onTimer未定义。setInterval在调用之前移动变量定义setInterval,它将起作用。

于 2012-10-02T16:16:31.987 回答
0
//like this blinkOff won't be called after the fadeIn
function blinkOn() { $blink.fadeIn( 500, blinkOff ); }
var blinkOff = function() { $blink.fadeOut( 500, blinkOn ); };

它会被调用。你只需要确保在分配之前(上面)blinkOn没有调用(引用是好的)。

于 2012-10-02T16:28:24.900 回答