this是js的关键字,当前环境执行期上下文对象的一个属性,在不同的环境,不用的作用下,表现也是不同的
全局上下文
无论是否在严格模式下,在全局执行环境中(在任何函数体外部)this 都指向全局对象。
console.log(this); // Window {postMessage: ƒ, blur: ƒ, focus: ƒ, close: ƒ, frames: Window, …}
console.log(window); // Window {postMessage: ƒ, blur: ƒ, focus: ƒ, close: ƒ, frames: Window, …}
console.log(window === this); // true
在全局下声明的变量都会挂载到window上,也可以理解在全局下this和window是同一个
var a = 1
var b = function(){
return 'function'
}
console.log(window.a); // 1
console.log(window.b); // ƒ (){ return 'function' }
console.log(window.a === a); // true
console.log(window.b === b); // true
函数上下文
var a = 'global -> a'
var obj = {
a: 'obj -> a',
test: function(){
console.log(a); // global -> a
console.log(window.a); // global -> a
console.log(this) // {a: "obj -> a", test: ƒ}
console.log(this.a); // obj -> a
}
}
obj.test()
谁调用的函数,那么函数内部的this指向默认就指向谁,上面的例子中,是obj调用的test方法,所以默认test的this指向是obj
var a = 1
function test() {
console.log(this); // window
console.log(this.a); // 1
}
test()
当代码在浏览器里执行时,全局作用域里的所有全局变量和函数都在window对象里定义,所以在全局函数里使用this,它指代window对象并储存着该对象的值
在松散模式下,函数可以返回this来获取全局对象,而在严格模式下,this返回的就是undefined
function test() {
'use strict'
console.log(this); // undefined
}
test()
上面也说了谁调用的函数,那么函数内部的this指向默认就指向谁,如果使用window.test的方式调用函数,this就会指向window
function test() {
'use strict'
console.log(this); // window
}
window.test()
在node环境中
var a = 'global -> a'
var obj = {
a: 'obj -> a',
test: function(){
console.log(window.a);
}
}
obj.test()
执行后就会报错
ReferenceError: window is not defined,在node中,全局是global。而且上面的var a = 'global -> a' 是不会挂载到global上的,
var a = 'global -> a'
var obj = {
a: 'obj -> a',
test: function(){
console.log(a); // 'global -> a'
console.log(global.a); // undefined
console.log(a === global.a); // false
console.log(global);
/*<ref *1> Object [global] {
global: [Circular *1],
clearInterval: [Function: clearInterval],
clearTimeout: [Function: clearTimeout],
setInterval: [Function: setInterval],
setTimeout: [Function: setTimeout] {
[Symbol(nodejs.util.promisify.custom)]:[Function(anonymous)]},
queueMicrotask: [Function: queueMicrotask],
clearImmediate: [Function: clearImmediate],
setImmediate: [Function: setImmediate] {
[Symbol(nodejs.util.promisify.custom)]: [Function (anonymous)]
}
}*/
}
}
obj.test()
可以看出,在global上就没有一个a的属性,如果要在全局上添加一个属性就需要手动的添加
global.xxxx = xxx
global.a = 'global -> a'
var obj = {
a: 'obj -> a',
test: function(){
console.log(a); // 'global -> a'
console.log(global.a); // 'global -> a'
console.log(a === global.a) // true
}
}
obj.test()
这时再打印global,它上面就有属性a了
获取全局对象的方法
浏览器环境
- 全局下的this
- window
- self
- frames
console.log(window);
console.log(this); // 全局下访问才能获取到全局对象
console.log(self);
console.log(frames);
var obj = {
test: function(){
console.log(window);
console.log(this);
console.log(self);
console.log(frames);
}
}
obj.test()
Snipaste_2021-06-14_14-37-49.png
node环境
- global
worker环境
- self
通用方式
- globalThis,在任何环境下都能获取到全局对象
console.log(globalThis);
浏览器环境:
不能在hbuilder的内置浏览器中查看,否则报错
“Uncaught ReferenceError: globalThis is not defined”
node环境
Snipaste_2021-06-14_14-49-04.png
worker不再演示
网友评论