2020年大前端面试题库+答案(第五章)如何判断this的指向

288 阅读3分钟

全局环境中

我们知道首先this并不会指向函数本身,无论是否在严格模式下,在全局执行环境中(在任何函数体外部)this 都指向全局对象。

函数(运行内)环境

1.简单调用

当函数在没有任何修饰的情况下,非严格模式下,this指向window,严格模式下this指向undefined.(默认绑定) 非严格模式,this的默认值指向全局对象

consle.log(this) //window

严格模式(当使用'use strict'后,成为严格模式)this将保持它进入执行环境的值,如果this没有被执行环境定义,那这时this指向undefined.

'use strict'
console.log(this) //undefined

当一个函数在其主体中使用this关键字时,可以通过使用函数继承自Function.prototype的call或apply方法将this值绑定到调用中的特定对象。(如果传递给this的值不是一个对象,javascript会尝试使用内部ToObject操作将其转换为对象。)

2当函数由一个对象引导调用时,this指向该对象。(隐式绑定)

function person(){
    console.log(this)  //obj
}
var obj = {name:'test',fun:person}
obj.fun();

当函数作为对象里的方法被调用时,它们的this是调用该函数的对象(此概念适用于原形链中this的getter与setter)

3.函数通过apply,call,bind绑定时,this指向绑定的对象(显式对象)

function person(name){
    console.log(name+':'+JSON.stringify(this))
}
var obj = {name:'lcy'}
person.bind(obj)('bind') //bind:{'name':'lcy'}
person.apply(obj,['apply']) //apply:{'name':'lcy'}
person.call(obj,'call') //call:{'name':'lcy'}

es5 引入了Function.prototype.bind.调用person.bind(obj)会创建一个与person具有相同函数体和作用域的函数,在这个新函数中,this将永久的被绑定到了bind的第一个参数,无论此函数是如何被调用的。

4.当函数被当作构造函数使用,又new引导调用时,this指向new创建出来的对象。(new绑定):

function person(name){
    this.name = name
}
var Person = new person('lcy')
//此时person方法中的this指向“Person”,因此可以使用Person.name获取到 name 的值
console.log(Person.name) //'lcy'

但是当构造函数中有返回对象或者函数时,this指向new创建出来的对象返回值;

下面代码中person.name = "qqqq",而不是this.name中设置的"aaaa"

function Person (name){
    //这时 下面 this.name = name;也会执行,但是不会起作用
    this.name = name
    return {name:'aaaa'}
}
var person = new Person('qqqq')
console.log(person.name) //'aaaa'

5.箭头函数其this取决于函数定义时所在的上下文。

function person(){
    this.fun1 = function(){
        console.log(this) //person
        return () =>{
            console.log(this) //person
        }
    }
    this.fun2 = function(){
        console.log(this) //person
        return function (){
            console.log(this) //window
        }
    }
}
var Person = new person()
//person 构造函数下的fun1 和fun2 都返回一个function
//并将整个function赋值给新的变量 fun1 、fun2
//此时fun1和fun2如果是在全局的作用域下,直接是window.fun1 和 window.fin2
//通过window.fun1和window.fun2调用方法,理论上方法中的this应该指向的是window
//但是箭头函数自身没有this,指向的只能是代码块所在的父级作用域,因此指向的是person构造函数中的fun1.
var fun1 = person.fun1()
var fun2 = person.fun2()
window.fun1()
window.fun2()

6.作为一个DOM事件处理函数

当函数被用作事件处理函数时,它的this是调用触发事件的元素(一些浏览器在使用非addEventListener的函数动态添加监听函数时不遵守这个约定)

7.作为一个内联事件处理函数

当代码被内联 on-event处理函数调用时,它的this指向箭头器所在的DOM元素。

本文摘自:

MDN/this

this指向

javascript中如何判断this的指向问题

每日语录:无论现在你处于什么状态,是时候对自己说:不为模糊不清的未来担忧,只为清清楚楚的现在努力。