如何向某人解释JavaScript关闭,知道它们所构成的概念(例如功能、变量等),但不了解关闭本身?
我已经在维基百科上看到了图表的例子,但不幸的是,它没有帮助。
如何向某人解释JavaScript关闭,知道它们所构成的概念(例如功能、变量等),但不了解关闭本身?
我已经在维基百科上看到了图表的例子,但不幸的是,它没有帮助。
当前回答
下面的简单例子涵盖了JavaScript关闭的所有主要点。
下面是一家工厂,生产可以添加和复制的计算机:
function make_calculator() {
var n = 0; // this calculator stores a single number n
return {
add: function(a) {
n += a;
return n;
},
multiply: function(a) {
n *= a;
return n;
}
};
}
first_calculator = make_calculator();
second_calculator = make_calculator();
first_calculator.add(3); // returns 3
second_calculator.add(400); // returns 400
first_calculator.multiply(11); // returns 33
second_calculator.multiply(10); // returns 4000
关键点:每个呼叫做_计算机创建一个新的本地变量n,该计算机的添加和复制功能在做_计算机返回后很长时间仍然可用。
内部函数,如添加和加倍,其访问变量在外部函数中声明**,被称为关闭。
这是几乎所有的关闭。
此分類上一篇
* 例如,它涵盖了在另一个答案中提供的“关闭为Dummies”文章中的所有点,除了例子6,这简单地表明,变量可以在被宣布之前使用,这是一个很好的事实,但完全与关闭无关。
** 任何外部功能,如果有几种是无缝的,甚至在全球背景下,因为这个答案清楚地表明。
其他回答
这里是一个简单的实时场景,只需阅读它,你会明白我们如何在这里使用关闭(看看座位数量如何变化)。
此前所解释的所有其他例子,也很好地理解这个概念。
function movieBooking(movieName) {
var bookedSeatCount = 0;
return function(name) {
++bookedSeatCount ;
alert( name + " - " + movieName + ", Seat - " + bookedSeatCount )
};
};
var MI1 = movieBooking("Mission Impossible 1 ");
var MI2 = movieBooking("Mission Impossible 2 ");
MI1("Mayur");
// alert
// Mayur - Mission Impossible 1, Seat - 1
MI1("Raju");
// alert
// Raju - Mission Impossible 1, Seat - 2
MI2("Priyanka");
// alert
// Raja - Mission Impossible 2, Seat - 1
也许我们应该切断你的27岁的朋友,因为整个“关闭”的概念是(!)...... voodoo!
我意思的是:(a)你不直觉地期望它......(b)当有人花时间向你解释它时,你肯定不会期望它工作!
当你终于意识到这样的事情是可能的,那么......肯定......任何人的后事实反应会是:“whoa-a-a(!)...... kew-el-l-l...(!!!)”
直觉给了你很多完全可靠的期望,这样的事情会“当然,绝对是无意义的,因此是完全不可能的。
正如我所说的那样,“这就是伏地。
MDN 解释我认为最好的:
关闭是指独立(自由)变量的函数,换句话说,关闭中定义的函数“记得”它创造的环境。
关闭总是有一个外部功能和一个内部功能. 内部功能是所有工作发生的地方,而外部功能只是保留内部功能创建的范围的环境。 这样,关闭的内部功能“记得”它创建的环境/范围。
var closure = function() {
var count = 0;
return function() {
count++;
console.log(count);
};
};
var counter = closure();
counter() // returns 1
counter() // returns 2
counter() // returns 3
在上面的代码中,计算是由外部函数(环境函数)保存的,所以每次你呼叫计算(),内部函数(工作函数)可以增加它。
关闭并不难理解,它只取决于观点。
我个人喜欢在日常生活中使用它们。
function createCar()
{
var rawMaterial = [/* lots of object */];
function transformation(rawMaterials)
{
/* lots of changement here */
return transformedMaterial;
}
var transformedMaterial = transformation(rawMaterial);
function assemblage(transformedMaterial)
{
/*Assemblage of parts*/
return car;
}
return assemblage(transformedMaterial);
}
我们只需要在某些情况下通过某些步骤,对于材料的转换,只有当你有零件时才有用。
下面是我最能给出的Zen答案:
你会期望这个代码做什么?在你运行它之前,在评论中告诉我!我很好奇!
function foo() {
var i = 1;
return function() {
console.log(i++);
}
}
var bar = foo();
bar();
bar();
bar();
var baz = foo();
baz();
baz();
baz();
现在,在您的浏览器中打开控制台(Ctrl + Shift + I 或 F12,希望)并插入代码并点击 Enter。
如果这个代码打印了你所期望的(JavaScript的新闻 - 忽略“未定义”的结尾),那么你已经有无语的理解。
我把它这样做,因为一旦我意识到这个代码将Foo()的内部函数的例子放在字符串和字符串中,然后通过这些变量呼叫它们,没有别的东西让我感到惊讶。
但如果我错了,并且控制台的输出让你惊讶,让我知道!