改变this的方法

2017-12-07  本文已影响0人  海山城

bind

bind,在Function.prototype上,返回一个新函数,并且使函数内部的this为传入的第一个参数

用法

var name = 'globle'
var App = {
  name: 'app',
  sayName: function(){
    console.log(this.name)
  }
}

var obj = {
  name: 'SeaMountC'
}

App.sayName()                     //"app"
App.sayName.bind(window)()        //"globle"
App.sayName.bind(obj)()           //"SeaMountC"

使用场景

var Page = {
  init: function(){
    this.node = document.body
    this.bind()
  },
  bind: function(){
    this.node.addEventListener('click', function(){
      this.sayHello()//①
    })
  },
  sayHello: function(){
    console.log('hello...' + this.node.innerText)
  }
}
Page.init() //报错

上述代码会报错,因为①处的this指的是this.node,而不是我们期待的Page,而document.body中并没有sayHello方法,所以报错。
修改方法:
第一种:将this存下来

var Page = {
  init: function(){
    this.node = document.body
    this.bind()
  },
  bind: function(){
    var _this = this
    this.node.addEventListener('click', function(){
      _this.sayHello() 
    })
  },
  sayHello: function(){
    console.log('hello...' + this.node.innerText)
  }
}
Page.init() //"hello...海山城"

参考前一遍写的this的判断方法,_this.sayHello() 相当于Page.sayHello.call(Page),因此sayHello中的this是指Page,没有问题

第二种:使用bind改变this

var Page = {
  init: function(){
    this.node = document.body
    this.bind()
  },
  bind: function(){
    this.node.addEventListener('click', function(){
      this.sayHello()
    }.bind(this))
  },
  sayHello: function(){
    console.log('hello...' + this.node.innerText)
  }
}
Page.init()

第三种:换种写法,同样使用bind改变this

var Page = {
  init: function(){
    this.node = document.body
    this.bind()
  },
  bind: function(){
    this.node.addEventListener('click', this.sayHello.bind(this))
  },
  sayHello: function(){
    console.log('hello...' + this.node.innerText)
  }
}
Page.init() //"hello...海山城"

注:

apply、call

bind与apply、call相同点:

bind与apply、call区别:

apply与call区别:

使用事例1
求和函数,直接arguments.forEach会报错,借用数组的forEach方法,通过call将forEach内部的this从数组改成arguments

function sum(){
//   ------------------报错-----------------
//   arguments.forEach(function(value){
//     console.log(value)
//   })
//   --------------------------------------
  
  var result = 0
  Array.prototype.forEach.call(arguments, function(value){
    console.log(value)
    result += value
  })
  console.log(result)
}
sum(9,5,4,3)

使用事例2
将arguments变成数组,这样就可以使用数组的方法了

function argsToArray(){
  var args = Array.prototype.slice.call(arguments, 0)
  console.log(args instanceof Array) //true
}
argsToArray(1,3,4,5,6)

使用事例3
借用Math.max(),Math.min()方法,求数组最大,最小值

var arr = [5, 0, 2, 9]
//------正常是这么调用的-------------
//Math.max(5, 0, 2, 9)
//-------------------------------------------

//使用apply
Math.max.apply(Math, arr)
Math.max.apply(null, arr)
上一篇 下一篇

猜你喜欢

热点阅读