该this关键字可以是非常混乱。本教程将帮助您了解其工作原理。您将了解如何this在不同的上下文和环境下工作。这些上下文包括全局对象,函数,对象和类的方法和事件。您还将了解globalthises2020中添加的新功能。
介绍该this是存在不只是在javascript中,而且在其他编程语言的特殊关键字。javascript的this不同之处在于在不同模式下的行为不同。在javascript中,有两种模式:严格和非严格。非严格模式是普通模式。有时也称为“马虎”模式。
什么this是指总是依赖于它定义的执行上下文。执行上下文是当前环境或范围,在其中声明正在执行的代码行。在运行时,javascript会维护所有执行上下文的堆栈。
该堆栈顶部的执行上下文是正在执行的上下文。当执行上下文更改时,更改的值也将this更改。让我们看一下this在不同上下文中指的是什么。
请注意严格模式严格模式旨在帮助您使javascript代码更简洁。它通过建立一些特殊规则来做到这一点。例如,必须先明确声明所有变量,然后才能为其分配值。您的函数必须在全局范围内声明。在函数内部,禁止对变量和函数参数使用相同的名称。
也禁止删除不可变的属性和不合格的标识符。所有这些以及许多其他事情都会引发错误。这是严格和非严格模式之间的另一个区别。在非严格模式下,许多错误是静默的。严格来说,它们不是。违反严格模式规则的所有内容都将引发错误。
除了这些规则外,严格模式还改变了this行为方式。为了更好的说明,我们将讨论如何在每个特定的上下文中。关于严格模式的最后一件事。如果要切换到严格模式'use strict';,请在代码顶部添加语句。
注意:您可以为所有代码或仅为特定功能打开严格模式。区别在于您在哪里使用该'use strict';语句。在全局范围的顶部使用它,它将应用于随后的所有代码。在函数顶部使用它,它将仅应用于该函数内部的代码。
全球范围内的“这个”在javascript中,当this在全局上下文中定义时this,默认情况下指的是global对象。对于浏览器,此全局对象是window对象。此全局对象是顶级范围。对于this全局上下文,严格模式没有任何区别。无论您处于严格模式还是非严格模式,this行为都将相同。
// global context and this in non-strict mode
console.log(this === window)
// true
// global context and this in strict mode
'use strict'
console.log(this === window)
// true
“ this”,全局上下文和node.js对于node.js,没有window对象。在node.js中,全局对象是一个特殊的对象,称为global。这意味着在全球范围内this将引用this?global。好吧,差不多。这仅在node.js内部是正确的。要对此进行测试,请首先启动您喜欢的控制台并输入node。
此命令将打开node.js环境,因此您可以直接使用它。之后,您可以测试this全局上下文中的引用。如果您的计算机上没有node.js,则可以从node.js?网站获取。
// in node environment
> console.log(this === global)
// true
> console.log(this)
// object [global] {
// global: [circular],
// clearinterval: [function: clearinterval],
// cleartimeout: [function: cleartimeout],
// setinterval: [function: setinterval],
// settimeout: [function: settimeout] { [symbol(util.promisify.custom)]: [function] },
// queuemicrotask: [function: queuemicrotask],
// clearimmediate: [function: clearimmediate],
// setimmediate: [function: setimmediate] {
// [symbol(util.promisify.custom)]: [function]
// }
// }
如果从javascript文件运行代码,结果将有所不同。当您在node.js中使用javascript文件时,本地代码仅限于该文件。那里的一切都不是全球性的,而是本地性的。结果,this不是指global,而是指module.exports。
// in node environment, in javascript file
console.log(this === global)
// false
console.log(this === module.exports)
// true
功能和“ this”对于javascript顶级功能,模式很重要。顶层是指在全局范围内声明的函数,而不是在对象或类内部声明的函数。如果您在非严格模式下工作,this则window在浏览器的情况下将引用全局对象。
// function in a non-strict mode
function testthis() {
console.log(this === window)
}
testthis()
// true
让我们use strict在函数顶部添加语句以打开严格模式。现在,结果将有所不同。this将不再引用全局对象,例如window。当您尝试获取thisjavascript?的值时将返回undefined。这是因为this现在未设置的值。
// function in a non-strict mode
function testthis() {
'use strict' // switch on strict mode for this function
console.log(this === window)
console.log(this)
}
testthis()
// false
// undefined
函数,this和call()和apply()有一种方法可以设置this您在调用函数时的值,而不必设置它undefined。为此,您可以使用call(),apply()或bind()方法。这称为“显式函数绑定”。当您使用这些方法之一时,您将this作为参数传递值。前两个call()和apply()几乎相同。
区别在于apply()接受参数列表与call()接受参数数组相同。apply()还允许您使用数组文字。
// set value of this with apply()
function testthiswithapply() {
'use strict'
console.log('value of this: ', this)
}
// set value of this to one
testthis.apply('one')
// 'value of this: one'
// set value of this with call()
function testthiswithcall() {
'use strict'
console.log('value of this: ', this)
}
// set value of this to one
testthis.call('one')
// 'value of this: one'
函数,this和bind()的bind()方法是不同的。当您要调用或调用一个函数时,不要使用此方法。而是使用该bind()方法来创建新的“绑定”函数。之后,您将调用新的“绑定”函数,而不是原始函数。现在,价值this就是您想要的价值。
// set value of this with bind()
function testthiswithbind() {
'use strict'
console.log('value of this: ', this)
}
// create bound function and set value of this to one
const newtestthiswithbind = testthiswithbind.bind('one')
// invoke new bound function newtestthiswithbind
newtestthiswithbind()
// 'value of this: one'
// or, with reassigning the original function
function testthiswithbind() {
'use strict'
console.log('value of this: ', this)
}
// create bound function and set valu