JavaScript 中 this 的详解

linshuai

this 的指向

this 是 js 中定义的关键字,它自动定义于每一个函数域内,但是它的指向却让人很迷惑。在实际应用中,this 的指向大致可以分为以下四种情况。

1.作为普通函数调用

当函数作为一个普通函数被调用,this 指向全局对象。在浏览器里,全局对象就是 window。

window.name = 'linxin';
function getName(){
    console.log(this.name);
}
getName();                   // linxin

可以看出,此时 this 指向了全局对象 window。
在ECMAScript5的严格模式下,这种情况 this 已经被规定不会指向全局对象了,而是 undefined。

'use strict';
function fun(){
    console.log(this);
}
fun();                      // undefined

2.作为对象的方法调用

当函数作为一个对象里的方法被调用,this 指向该对象

var obj = {
    name : 'linxin',
    getName : function(){
        console.log(this.name);
    }
}

obj.getName();              // linxin

如果把对象的方法赋值给一个变量,再调用这个变量:

var obj = {
    fun1 : function(){
        console.log(this);
    }
}
var fun2 = obj.fun1;
fun2();                     // window

此时调用 fun2 方法 输出了 window 对象,说明此时 this 指向了全局对象。给 fun2 赋值,其实是相当于:

var fun2 = function(){
    console.log(this);
}

可以看出,此时的 this 已经跟 obj 没有任何关系了。这时 fun2 是作为普通函数调用。

3.作为构造函数调用

js中没有类,但是可以从构造器中创建对象,并提供了 new 运算符来进行调用该构造器。构造器的外表跟普通函数一样,大部分的函数都可以当做构造器使用。当构造函数被调用时,this 指向了该构造函数实例化出来的对象。

var Person = function(){
    this.name = 'linxin';
}
var obj = new Person();
console.log(obj.name);      // linxin

如果构造函数显式的返回一个对象,那么 this 则会指向该对象。

var Person = function(){
    this.name = 'linxin';
    return {
        name : 'linshuai'
    }
}
var obj = new Person();
console.log(obj.name);      // linshuai

如果该函数不用 new 调用,当作普通函数执行,那么 this 依然指向全局对象。

4.call() 或 apply() 调用

通过调用函数的 call() 或 apply() 方法可动态的改变 this 的指向。

var obj1 = {
    name : 'linxin',
    getName : function(){
        console.log(this.name);
    }
}
var obj2 = {
    name : 'linshuai'
}

obj1.getName();             // linxin
obj1.getName.call(obj2);    // linshuai
obj1.getName.apply(obj2);   // linshuai

这两个方法在js中都是非常常用的方法,可以阅读下一篇:javascript 中 apply 、call 的详解

更多文章:lin-xin/blog

阅读 1.5k

爱前端
文章首发于:[链接] 作为一名前端开发者,我会把平时积累的一些经验写成文章,进行分享,一起学习进步!
1 篇内容引用
4.4k 声望
0 粉丝
0 条评论
推荐阅读
JS实现的接粽子小游戏,愿你好运接粽而至
端午节虽然已经过了,但是美好的生活以旧在继续。这里用 JS 实现了一个简单的接粽子小游戏,寓意美好接粽而至。能接到多少粽子,完全看你手速,不用担心端午没粽子了。线上体验地址

linshuai2阅读 2.5k评论 1

还在用定时器吗?借助 CSS 来监听事件
平时工作中很多场合都要用到定时器,比如延迟加载、定时查询等等,但定时器的控制有时候会有些许麻烦,比如鼠标移入停止、移出再重新开始。这次介绍几个借助 CSS 来更好的控制定时器的方法,一起了解一下吧,相信...

XboxYan29阅读 2k评论 2

封面图
如何优雅地中断 Promise?来试试 AbortController 吧!
欢迎大家来到 前端小课堂 的第五期,今天我们来聊一聊如何终止正在进行中的 Fetch 以及 Promise。文中会跟大家详细介绍这里面的两个关键知识点 AbortController 和 AbortSignal。对动手实践比较感兴趣的同学还可...

dreamapplehappy23阅读 2.8k评论 4

封面图
前端性能优化(图文并茂,通俗易懂)
默认情况下,我们静态导入的所有模块都会添加到初始捆绑包中。使用默认 ES2015 导入语法 导入的模块将静态导入。import module from 'module'

寒水寺一禅26阅读 2.8k评论 1

超强的苹果官网滚动文字特效实现
每年的苹果新产品发布,其官网都会配套更新相应的单页滚动产品介绍页。其中的动画特效都非常有意思,今年 iPhone 14 Pro 的介绍页不例外。最近,刚好有朋友问到,其对官网的一段文字特效特别感兴趣,看适用简单却...

chokcoco24阅读 1.6k

封面图
50天用vue3完成了50个web项目,我学到了什么?
通过本文的50个web示例你将学到:Vue3核心基础语法和进阶语法less核心基础语法和进阶语法scss核心基础语法和进阶语法1.Expanding Cards效果如图所示:源码在线示例学到了什么?JavascriptVue ref方法定义基本响应式...

夕水21阅读 2k

封面图
一个被忽略的前端细分领域
大家好,我卡颂。回想下你学新技术的主要途径是什么?看书?看技术文档?看博文?看视频?归纳起来,无外乎文字、视频两种形式。从纸媒时代到互联网时代,再到移动互联网时代,虽然信息的载体发生变化,但信息的...

卡颂18阅读 1.4k

封面图
4.4k 声望
2.1k 粉丝
宣传栏