闭包中的Javascript值
Javascript value in closure
我真的无法解释自己为什么创建闭包失败,我在下面的代码中得到了undefined
:
function A() {
this.p1=1;
this.p2=2;
this.f1=function(){
alert(this.p1);
}
this.f2=function(){
alert(this.p2);
}
this.action=function(param){
if (param=='1')
return this.f1;//by case
else if (param=='2')
return this.f2;
};
}
var v=new A();
v.action("1")();
这与闭包无关。
您正在从方法返回一个函数引用,当您调用它时,您希望它作为对象中的方法执行,但它是作为全局作用域作为上下文的函数执行的。
使用call
方法在对象的上下文中调用函数:
v.action("1").call(v);
在我看来,你不是100%确定闭包是什么…从你的代码开始:
function A()
{
this.p1=1;//public
var p2=2;//private
this.f1=function()
{
alert(this.p1);
};
this.f2=function()
{
alert(p2);
};
在这里,我已经将p2
定义为构造函数作用域的局部变量,但是公共方法f2
可以访问它的值,甚至可以更改它。这是一个闭包:代码/数据包含在它自己的特定范围内。你用以下代码做什么:
this.action=function(param)
{
if (param=='1')
{
return this.f1;
}
return this.f2;
};
}
var v=new A();
v.action("1")();
与闭包几乎没有关系,您正在返回对函数的引用(在这种特定情况下,它恰好是一个对象方法)。为什么,这个point
不属于它来自的对象?简单:
var foo = {name:'someObject'};
foo.retVal = v.action('1');//returns function
//much later:
foo.retVal();
你还会期望this
指向v
吗?那不是很难调试吗?在调用函数(方法与否)时,this
将是调用该函数的上下文对象的指针。一旦v.action('1')
返回,在您的示例中,函数将返回到全局对象,因此它将指向this
或window
函数没有绑定到特定的this,也就是说:
(function() { console.log(this) })(); // Window
您可以使用call方法,或者(更好)使用.bind方法(确保旧浏览器使用polyfill):
function A() {
this.p1 = 1;
this.p2 = 2;
}
A.prototype.f1 = function() {alert(this.p1)};
A.prototype.f2 = function() {alert(this.p2)};
A.prototype.action = function(param) {
if ('1' == param) {
return this.f1.bind(this);
} else if (param == '2') {
return this.f2.bind(this);
}
};
var v = new A();
v.action("1")(); // 1
bind方法返回一个新函数,该函数将使用此集合调用bind参数的原始函数。Function.prototype.bind MDN 文档
v.action("1")
与action.call(v, "1")
大致相同
在这样的闭包中,当稍后调用时,"this"实际上指的是Window。为了避免这种情况,您需要将"this"分配给另一个变量,如"that":
function A() {
var that = this;
that.p1=1;
that.p2=2;
that.f1=function(){
alert(that.p1);
}
that.f2=function(){
alert(that.p2);
}
that.action=function(param){
if (param=='1')
return that.f1;//by case
else if (param=='2')
return that.f2;
};
}
var v=new A();
v.action("1")();
在嵌套函数this
中还有另一层含义。尝试使用变量在内部传递引用,请参阅jsfiddle。
如您所愿
v.action("1")
返回定义为的函数
function(){
alert(this.p1);
}
你也可以通过添加一对括号来调用它,就像你所做的那样。但是,该函数中的this
将绑定到全局对象(在浏览器中为window
)。而CCD_ 17就是CCD_。这就是你得到的输出。
如前所述,您可以通过使用call
而不是括号来调用函数来决定什么应该是this
:
v.action("1").call(v);
this
在JavaScript中的含义相当混乱。帮助我理解的解释可以在《十分钟内的Javascript》的3.3一节中找到。这(严重的灾难)的含义(尽管整个文档需要十多分钟的时间,但值得一读)。
- for循环中的JavaScript闭包
- Javascript闭包-如何防止内存泄漏
- Javascript.闭包和dynamic'这'实际上具有约束力
- 用于添加两个数字的javascript闭包的用法
- 什么'这个javascript闭包的区别是什么
- 我可以使用JavaScript闭包添加数字吗
- javascript闭包:保护内部变量
- JavaScript闭包&回调函数
- 这些被认为是Javascript闭包吗
- JSHint 错误“对象不支持此属性或方法”用于 javascript 闭包
- JavaScript闭包的效果如何
- JavaScript 闭包和 for 循环
- 在谷歌地图示例中为 Ajax 调用制作一个 JavaScript 闭包
- JavaScript闭包和返回数组元素
- 如何在严格模式下实现以下JavaScript闭包
- 请解释这个Javascript闭包练习
- JavaScript闭包和变量引用
- Javascript闭包覆盖函数表达式
- Javascript闭包错误
- 为什么JavaScript闭包不能与预定义的函数一起使用