简体   繁体   English

不了解Javascript中的范围

[英]Not understanding scope in Javascript

I don't quite understand this bit of code. 我不太明白这段代码。

$('div').click((function () { 
    var number = 0;
    return function () {
        alert(++number);
    };
})());

My understanding is: 我的理解是:

  • An anonymous function is defined and assigned to the click handler. 定义匿名函数并将其分配给单击处理程序。

  • When I click on div, this function is invoked. 当我单击div时,将调用此函数。

What the function does is: 该功能的作用是:

  • Define a variable number = 0 定义变量number = 0

  • Return ++number 返回++number

So why does the number in alert increment every time I click? 那么为什么每次点击时警报的数量会增加? Shouldn't number be reset to 0 every time I click? 每次点击都不应该将number重置为0?

Here you've got a self-invoking function , which returns a function. 在这里你有一个自动调用函数 ,它返回一个函数。 Watch out for the brackets at the end: 注意最后的括号:

(function () { 
    var number = 0;
    return function () {
        alert(++number);
    };
})()

So the callback of the click handler is only the returned inner function : 所以click处理程序的回调只是返回的内部函数

function () {
    alert(++number);
};

This inner function has access to the variable number , which is in the scope of the outer function. 此内部函数可以访问变量number ,该变量在外部函数的范围内。

So your code can also be written as follows: 所以你的代码也可以写成如下:

function outerFunction() {
    var number = 0;
    return function () {
        alert(++number);
    };
};

var innerFunction = outerFunction();

$('div').click(innerFunction);

If we used (ugly) names for the anonymous functions, your code could be rewritten as: 如果我们为匿名函数使用(丑陋)名称,则可以将代码重写为:

$('div').click((function makeIncrementer() {
    var number = 0;
    return function incrementAndAlert() {
        alert(++number);
    };
})());

More verbose code retaining similar semantics would be: 保留类似语义的更详细代码将是:

var makeIncrementer = function() {
    var number = 0;
    return function() { alert(++number); };
};

var incrementAndAlert = makeIncrementer(); // function() { alert(++number); }

$('div').click(incrementAndAlert);

makeIncrementer is a function that, when called, defines a number variable in its scope, and returns a function - note that makeIncrementer doesn't increment, nor alert the number variable, instead it returns another function that does just that. makeIncrementer是一个函数,在调用时,在其作用域中定义一个number变量,并返回一个函数 - 注意makeIncrementer不递增,也不警告number变量,而是返回另一个函数。

Now incrementAndAlert is bound to this returned function 现在incrementAndAlert绑定到这个返回的函数

function() { alert(++number); }

that captures makeIncrementer 's number variable, which enables it to keep number 's state between incrementAndAlert calls triggered by $('div') clicks. 它捕获makeIncrementernumber变量,这使它能够在$('div')点击触发的incrementAndAlert调用之间保持number的状态。

This is not an "answer", but hopefully it will show a different way of looking at the problem. 这不是一个“答案”,但希望它会以不同的方式来看待问题。


First off, note that JavaScript functions are just objects and are thus just values that can be bound to variables. 首先,请注意JavaScript函数只是对象,因此只是可以绑定到变量的值。 As such, 因此,

$('div').click((function () { 
    var number = 0;
    return function () {
        alert(++number);
    };
})());

can be, with a simple expression substitution, rewritten as 可以通过简单的表达式替换重写为

var f = function () { 
    var number = 0;
    return function () {
        alert(++number);
    };
};
// $('div').click((f)()); and when removing extra parenthesis ->
$('div').click(f());

Then, after one more simple expression substitution 然后,经过一次简单的表达式替换

var g = f()
$('div').click(g);

it should be clear that the (outer) function, f , is invoked first and it is the resulting (inner function) value, g , that is used as the handler. 应该清楚的是,首先调用(外部)函数f ,它是用作处理程序的结果(内部函数)值g

Aside from introducing variables, the above substitutions are semantically equivalent to the original code. 除了引入变量之外,上述替换在语义上等同于原始代码。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM