JavaScript之this

发布时间:2019-08-15 发布网站:脚本宝典
脚本宝典收集整理的这篇文章主要介绍了JavaScript之this脚本宝典觉得挺不错的,现在分享给大家,也给大家做个参考。
本文共 1065 字,读完只需 4 分钟

概述

在 JAVA 中,this 的概念很透彻,就是指向当前对象(方法和属性的持有者),在编译的时候就能确定 this 指代,而由于 JavaScript 中 this 是动态绑定,或称为运行期绑定的,在绝大多数情况下,函数的调用方式决定了 this 的值,所以在 JS 中不能在定义时决定地定义 this 是哪个上下文对象。

this 的指向只和函数的调用位置(方式)有关,和函数声明的位置无关。

本文就从 this 应用场景调用方式的角度,解析 this 的用法。

首先,要知道,this 的作用是什么

函数体内部,指代函数当前的运行上下文。

一、全局上下文

在全局上下文中,this 指向全局对象,在浏览器中指向 window,在 NodeJs 中指向 global。

VAR a = "全局";
console.LOG(this)  // 浏览器:window
console.log(this)  // nodejs:global
console.log(this.a)  // "全局"

这是 JS 中的默认绑定,在全局上下文中,this 会默认绑定到 全局对象。

二、函数声明

在非严格模式下,未加关键字 var 声明的变量,会成为全局对象下的属性,所以,此时
在严格模式下,this 将保持他进入执行上下文时的值,所以下面的 this 将会默认为 undefined

function foo() {
    "use strict";
    console.log(this);
}

foo();  // undefined 严格模式

上述也是 JS 中 this 的默认绑定,在函数定义中,函数中的 this 会默认绑定到全局对象或者 undefined。

当函数作为对象里的方法被调用时,函数中 this 是调用该函数的对象。
function foo() {
    console.log("foo");
}

var obj = {
    this.bar = "bar";
    this.foo = foo;
}

obj.foo(); // "foo"

在调用位置,是 obj 对象调用了 foo 函数,此时 this 就指向了 obj 对象。

function foo() {
    console.log(this.bar);
}

var obj2 =  {
    bar: "2",
    foo: foo
}

var obj1 = {
    bar: "1",
    obj2: obj2
}

obj1.obj2.foo()  // "2";

这是 JS 中 this 的隐式绑定,this 会隐式绑定到调用的最近一层上下文对象。

三、call & apply

其实在函数中,函数正确的调用应该是用 call, apply 函数的形式。

function foo() {
    console.log(this.bar);
}

let obj = {
    bar: "1",
    foo: foo
}

obj.foo();  // `.` 点调用其实是语法糖

foo.call(obj)  // 1 正确的姿势
foo.apply(obj) // 1

这是 JS 中 this 的显式绑定,函数通过从 call 和 apply 函数可以显式指定函数的调用对象。

ES5 提供了一个 bind()方法:

let obj2 = {
    a: 2
}

let foo = function () {
    console.log(this.a);
}

let bar = foo.bind(obj2);
bar() // 2;

就是 JS 中 this 的硬绑定,bind() 函数会返回一个指定了调用对象的函数,返回的函数的被指定了 this 且 this 无法改变

四、构造函数

当函数加上关键字 new 后,函数会变成一个构造函数,此时构造函数中的 this 指向即将创建的对象实例,同时对象实例会关联到构造函数的原型对象 prototype 上。

function Foo() {
    this.a = 3;
}

var obj = new Foo();

obj.a // 3

五、箭头函数

ES6 中,提供了函数定义的语法糖,让定义函数变得更简洁(没有 arguments, 没有原型)。同时上面四条绑定规则在箭头函数中不适用,使得 this 的查找更可控。

// 一般函数:
var a = 1;
var obj = {
  a: 2,
  say: function() {
    console.log(this.a)
  }
}
obj.say();  // console.log 打印值为 2

// 箭头函数
var a = 1;
var obj = {
  a: 2,
  say: () => {
    console.log(this.a)
  }
}
obj.say(); // 1   !!!

由于箭头函数定义时, obj {} 不是执行上下文,say 变量引用的箭头函数,其 this 是父级执行上下文,也就是全局上下文,所以 this.a 就是 全局变量 a: 1;

在箭头函数中,this 与封闭词法上下文的 this 保持一致,this 被永久绑定到了它最近一层非箭头函数的 this,而与函数的调用位置无关。

总结

在绝大多数情况下,函数的调用方式决定了 this 的值,但最终都指向了调用了它的那个上下文对象。

欢迎关注我的个人公众号“谢南波”,专注分享原创文章

JavaScript之this

脚本宝典总结

以上是脚本宝典为你收集整理的JavaScript之this全部内容,希望文章能够帮你解决JavaScript之this所遇到的问题。

如果觉得脚本宝典网站内容还不错,欢迎将脚本宝典推荐好友。

本图文内容来源于网友网络收集整理提供,作为学习参考使用,版权属于原作者。
如您有任何意见或建议可联系处理。小编QQ:384754419,请注明来意。