this 的定义
this 是一个指针,指向的是函数执行的环境对象。
用几个例子说明 this 的指向
- 普通函数内的 this 指向执行环境对象,例子中的执行环境是 window
var a = 'window'
function fn(){
let a = 'fn'
return this.a
}
fn(); // 'window'
- 构造函数创建的对象的函数内的 this 指向该对象,例子中的 this 指向是 obj
function Fn(){
this.a = 'Fn'
this.getA = function(){
return this.a
}
}
var obj = new Fn() // {a:'Fn',getA(){return this.a}}
obj.a; // 'Fn'
obj.getA() // 'Fn'
- 对象中的函数内的 this 指向对象本身,即对象为该函数的执行环境。其本质是上例子的语法糖。
var a = 'window'
var obj = {
a: 'obj',
getA(){
return this.a
}
}
obj.getA(); // 'obj'
- 赋值可能会使函数内的 this 指向发生改变
var a = 'window'
var obj1 = {
a: 'obj1',
getA: null
}
var obj2 = {
a: 'obj2',
getA(){
return this.a
}
}
console.log(obj2.getA()) // 'obj2'
obj1.getA = obj2.getA
console.log(obj1.getA()) // 'obj1'
var getA = obj2.getA
console.log(getA()) // 'window'
- call() 和 apply() 方法可改变运行函数的作用域,两个方法首个参数都是传入"运行函数的作用域",例子中的 this 指向 obj1 和匿名对象。(文章最后简单讲述两个函数的介绍)
obj1 = { a: 'obj1' }
obj2 = {
a: 'obj2',
getA(){
return this.a
}
}
var aValue = obj2.getA.apply(obj1); // 'obj1'
// 也可以传入匿名对象
var aValue = obj2.getA.apply({a:'anonymity'}); // 'anonymity'
apply() 和 call() 的差异及用法
- apply() 接收两个参数:运行的作用域(不指定可以填 null ) 和 传递给函数的参数所组成的数组(或"类数组") 。
var baseNum = 20
var obj = { baseNum: 10 }
function computer(addend, divisor) {
let result = this.baseNum || 0
return (result + addend) / divisor
}
var num = computer.apply(obj, [2, 5]); // (10+2)/5=2.4
// 可以把函数的 arguments 传递给 "apply"
function computer2(addend, divisor) {
return computer.apply(this, arguments)
}
var num2 = computer2(2, 5); // (20+2)/5=4.4
- call() 与 apply() 类似,区别在于 "call" 接受的是若干个参数的列表,不多赘述。
var num = computer.call(obj, 2, 5); // 所有参数展开传递