在绝大多数情况下,函数的调用方法决定了this的值(运行时绑定)。this不能在执行期间被赋值,并且在每次函数呗调用时this的值也可能会不同。
在非严格模式下,总是指向一个对象,在严格模式下可以是任意值。
全局执行环境中,指向全局对象window(非严格模式、严格模式)
在函数内部,取决于函数被调用的方式
⑴ 直接调用时的this值:
① 非严格模式:全局对象(window)
② 严格模式:undefined
⑵对象方法调用时的this值
① 调用者
// ------------- 1.全局执行环境 -------------
// 严格模式,非严格模式 全局对象(window)
// 'use strict'
// console.log(this)
// ------------- 2.函数内部 -------------
// 2.1 直接调用-非严格模式
// function func() {
// console.log(this) // window
// }
// func()
// 2.1 直接调用-严格模式
// function func() {
// 'use strict'
// console.log(this) // undefined
// }
// func()
// 2.2 对象方法调用
const food = {
name: '猪脚饭',
eat() {
'use strict'
console.log(this)
}
}
// 非严格模式,严格模式
food.eat() // 调用者food对象
严格模式是采用具有限制性JavaScript变体的一种方式,从而使代码隐式地脱离“马虎模式/稀松模式/懒散模式“(sloppy)模式。
// 1.为整个脚本开启严格模式
'use strict'
function func(){
// 2.为函数开启严格模式
'use strict'
}
需要注意的是 这两中开启严格模式的方法 ‘use strict’ 这一段代码都需要写在最顶端,它的上面不能有别的代码(不包括注释)
func.call(thisArg,参数1,参数2...)
func.apply(thisArg,[参数1,参数2...])
// ------------- 1. 调用时指定this: -------------
function func (numA, numB) {
console.log(this)
console.log(numA, numB)
}
const person = {
name: 'zhangsan'
}
// 1.1 call:挨个传入参数
func.call(person, 1, 2)
// 1.2 apply:以数组的方式传入参数
func.apply(person, [3, 4])
const bindFunc=func.bind(thisArg,绑定参数1,绑定参数2...)
function func (numA, numB) {
console.log(this)
console.log(numA, numB)
}
const person = {
name: 'zhangsan'
}
// 2.1 bind方法
const bindFunc = func.bind(person, 666)
bindFunc(888)
const person = {
name: 'zhangsan',
sayHi () {
//这个箭头函数是写在sayHi方法里面的这个this的值取决于sayHi的this
setTimeout(() => { console.log(this) })
}
}
const food = {
name: '西兰花炒蛋',
eat () {
console.log(this,1)
setTimeout(() => {
console.log(this,2)
}, 1000)
setTimeout(function () {
console.log(this,3)
}, 1000)
}
}
food.eat()