我想了解this
,而且它在这里混淆了我一下:
var randomFunction = function(callback) {
var data = 10;
callback(data);
};
var obj = {
initialData: 20,
sumData: function(data) {
var sum = this.initialData + data;
console.log(sum);
},
prepareRandomFunction: function() {
randomFunction(this.sumData.bind(this));
}
};
obj.prepareRandomFunction();
是this
设计来为自己在那里的代码首先呈现? 举例来说,在我的例子中,我成功地用它来指obj
,也结合了功能obj
,但由于this
被作为回调函数传递,什么是被设置为阻止它randomFunction
(即什么是从停止它从字面上传递“this.sumData.bind(本)”,让this
被设置为randomFunction
时,它会从那里叫)?
我努力学习一个小白。 谢谢。
更新我不完全问这通常是如何工作的(我不认为)。 我主要想知道为什么this
被设置在那里我把它定义为我的论点randomFunction
调用,而不是其中callback
被称为内randomFunction
。 我可能是错的,但如果我是交换this.sumData.bind(this)
与callback(data)
,我现在有,我想我会得到不同的结果。 那是因为callback
是一个参考this.sumData.bind(this)
,当它被首先定义(并在this
是obj
)?
我想我已经通过这个场景,了解到this
时候它的执行设置。 它不是通过作为参数来当参数被称为上下行以后设置。
this
函数调用中被按照功能是如何被调用设置。 有迹象表明,六个主要途径this
被设定。
正常的函数调用:在正常的函数调用,如foo()
this
被设置为全局对象(这是window
的浏览器),或者undefined
(在Javascript的严格模式)。
方法调用:如果一个方法被称为诸如obj.foo()
则this
被设置为obj
在函数内。
。适用()或.CALL():如果.apply()
或.call()
被使用,然后this
根据什么被传递到被设置.apply()
或.call()
例如,你可以做foo.call(myObj)
,并导致this
设置为myObj
的内部foo()
为特定的函数调用。
使用新:如果你调用一个函数new
如new foo()
然后创建一个新的对象,并在构造函数foo
调用与this
设置为新创建的对象。
使用.bind():当使用.bind()
一个新的存根函数是从内部使用的是调用返回.apply()
来设置this
指针传递给.bind()
仅供参考,这是不是一个真正的不同情况,因为.bind()
可以实现.apply()
使用ES6脂肪Arrow功能通过在ES6 +箭头语法定义功能将当前词汇值绑定this
给它。 所以,不管功能如何在其他地方调用, this
值将被解释该值设置this
有定义的功能时。 这是比所有其他函数调用完全不同。
有排序第七的方法,通过一个回调函数 ,但它不是真正的自己的方案,而是调用回调函数使用上述方案中的一种,并决定价值来决定this
将是回调时被调用。 您要咨询无论是文档或代码,调用函数或测试它自己来决定什么this
会在回调中被设置为。
什么是重要的Javascript理解的是,在Javascript中的每一个函数或方法调用设置了一个新值this
。 而且,该值设置由函数如何调用确定。
所以,如果你传递一个方法,一个普通的回调,该方法不会默认情况下,获取尽可能称为obj.method()
因此不会有正确的价值this
一套吧。 您可以使用.bind()
来解决这个问题。
这也是有用的知道一些回调函数(如DOM事件处理程序)被调用的特定值this
是通过调用回调函数的基础设置。 在内部,它们都使用.call()
或.apply()
所以这不是一个新的规则,而是一个需要注意的。 该“契约”的一个回调函数可能包括如何进行设置的值this
。 如果没有明确设置的值, this
,那么它会根据规则1#设置。
在ES6,经由箭头函数调用的函数,维持的当前词汇值this
。 这里的阵列功能保持词汇的例子this
从MDN :
function Person(){
this.age = 0;
setInterval(() => {
this.age++; // |this| properly refers to the person object
}, 1000);
}
var p = new Person();
您的示例obj.prepareRandomFunction();
是规则#2的上方, this
将被设置为obj
。
您的示例randomFunction(this.sumData.bind(this))
是规则#1的上方,从而this
内randomFunction
将被设置为全局对象或undefined
(如果在严格模式)。
由于randomFunction正在呼叫它本身使用的回调函数.bind()
则的值this
时它被称为将被设置到的值的回调函数内this
传递给.bind()
中this.sumData.bind(this)
,经由上述规则#5。 .bind()
实际上创建了一个新的功能,谁的工作是调用原来的功能后再进行设定的自定义值this
。
下面是关于该主题的其他几个引用:
如何避免“本”指的DOM元素,并参照对象
更好地理解这个
如何将“this”关键字的工作?
请注意,在使用的.apply()
或.call()
或.bind()
您可以创建一个有些奇怪的东西各种各样,有时是非常有用的东西,不可能在像C ++来完成。 你可以使用任何函数或方法在世界上并调用它,好像它是一些其他对象的方法。
例如,这通常被用来使在该项目的副本arguments
对象到一个数组:
var args = Array.prototype.slice.call(arguments, 0);
或类似的:
var args = [].slice.call(arguments, 0);
这需要阵列的.slice()
方法并调用它,而是用一个参数对象作为其供给this
指针。 的arguments
对象(虽然不是一个实际的阵列),具有使刚好足够的阵列一样的功能.slice()
方法可以在其上操作,并且它最终使的副本arguments
物品进入其然后可被操作上的实际阵列直接与真正的数组操作。 这种类型的欺骗,不能不管三七二十一完成。 如果阵列.slice()
方法依赖于其他阵列方法中不存在对arguments
对象,那么这招是行不通的,但是因为它仅依赖于[]
和.length
,这两者的arguments
对象具有,它不实际工作。
所以,这一招可以用“借”从任何对象的方法,并将其作为长期应用到另一个对象,你是把它们应用到任何支持的方法或该方法实际使用属性的对象。 这不是在C做++,因为方法和属性是“硬约束”在编译时间(++必将在编译时设立了专门v表转位置C甚至是虚拟的方法),但可以在JavaScript中很容易做到,因为性质和方法,在现场通过运行时的实际名称,以便包含正确的属性和方法将与这些操作的任何方法,任何工作对象抬头。
一步步。
1) this
内部prepareRandomFunction
是obj
obj.prepareRandomFunction()
2) randomFunction
取一个函数:
randomFunction(this.sumData);
3)函数被调用:
callback(data);
通知callback
被不带一个点,这意味着它具有用于没有价值this
,这意味着this
是全局对象(或undefined
严格模式)。
4) sumData
被调用:
var sum = this.initialData + data;
this
是全局对象, initialData
不存在,您添加undefined
到data
。 意想不到的效果。
解决方法:绑定this
永久:
randomFunction(this.sumData.bind(this));
4) sumData
运行时, this
是obj
, obj.initialData
是20
。 有用。
这是专为自己设置它在代码首先呈现?
不,这是通过一个函数是如何调用或通过使用绑定设置。
举例来说,在我的例子中,我成功地用它来指OBJ
由于该功能是使用所谓的:
obj.prepareRandomFunction();
其中规定在此为obj功能。
并且还结合了功能OBJ
在:
var obj = {
...
prepareRandomFunction: function() {
randomFunction(this.sumData.bind(this));
}
};
因为prepareRandomFunction被称为所有与obj为这一点 ,那么内obj.sumData的这个值设置为OBJ,并调用randomFunction有效地解析为:
randomFunction(obj.sumData.bind(obj));
但因为这是被作为一个回调函数传递,什么是被设定为randomFunction停止它
您设定这样一个事实在通话OBJ。 如果你想这是randomFunction,您需要将其设置为。 randomFunction对这个没有内在价值,它是由该函数的调用(或使用绑定的)设置。
(即什么是从字面上传递“this.sumData.bind(本)”,因此,这是设置为randomFunction停止它)?
因为这不是randomFunction时执行该代码。
所以:
obj.prepareRandomFunction();
这一套到obj,然后做(用OBJ更换这就要求prepareRandomFunction:
randomFunction(obj.sumData.bind(obj));
在randomFunction, 这并没有被设置成默认为全局对象(无关真的,因为它是这里没有使用)。 然后:
var randomFunction = function(callback) {
var data = 10;
callback(data);
};
与值10创建一个局部变量的数据 ,然后用它的这一套来的obj调用sumData和传递数据的价值。 然后:
sumData: function(data) {
var sum = this.initialData + data;
console.log(sum);
},
而且由于这是OBJ,分配有效解决到:
var sum = obj.initialData + 10;
这是30。
这是一种自 - 对象的参考。 运营商,宣布其作为对象 - - 当你,或者通过使用新创建对象文本或
通过调用JS的内置-in的之一,这将要被分配给它。
但随着JS的作用域是动态的,而不是非 - 短暂的,你通常不能依靠这个太多了 - 对象。 这就是为什么你经常看到的结构,如oThis:本或VARØ