【js】this指向

定义

this指的是函数运行时所在的环境。

运行环境

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

var x = 1;
var obj = {
  f: f, // 把上面的函数f()赋值给属性f;在内存中,f属性存放的是函数f()的地址,所以调用的是f()的引用地址
  x: 2,
};

// 全局环境执行,this指向全局变量,即 this.x 指向全局环境的x
f() // 1

// obj 环境执行,this.x指向obj.x
obj.f() // 2

示意图:

  • 全局环境中

在这里插入图片描述

  • obj环境中

在这里插入图片描述

this的四种用法

第一种:纯粹的函数调用

这是函数的最通常用法,属于 全局性调用,因此 this就代表全局对象

var x = 1;
function test() {
   console.log(this.x);
}
test();  // 1
第二种:作为对象方法的调用

函数还可以作为某个对象的方法调用,这时this就指这个对象

   function test() {
      console.log(this.x);
    }

    var obj = {};
    obj.x = 1;
    obj.m = test;

    obj.m(); // 1
第三种:作为构造函数调用

this就指这个新对象

var x = 2;
function test() {
  this.x = 1;
}

var obj = new test();
obj.x // 1

x  // 2,全局变量x的值根本没变
第四种:apply、call、bind 调用
var x = 0;
function test() {
 console.log(this.x);
}

var obj = {};
obj.x = 1;
obj.m = test;
obj.m.apply() // 0,this指的是全局对象
obj.m.apply(obj); //1,this指的是对象obj
  • apply()的参数为空时,默认调用全局对象(重点)

call()方法:

  • 函数名称.call(obj,arg1,arg2...argN);
  • 参数说明:
  • obj:this要指向的对象,
  • arg1,arg2…argN :参数列表,参数与参数之间使用一个逗号隔开
  • 临时改变一次this指向,并立即执行

apply()方法:

  • 函数名称.apply(obj,[arg1,arg2...,argN]);
  • 参数说明:
  • obj:this要指向的对象
  • [arg1,arg2…argN]:参数列表,要求格式为数组
  • 临时改变一次this指向,并立即执行

bind方法:

  • 函数名称.bind(obj,arg1,arg2...argN);
  • 参数说明:
  • obj:this要指向的对象,
  • arg1,arg2…argN :参数列表,参数与参数之间使用一个逗号隔开(可以分多次传入,call则必须一次性传入所有参数)
  • 改变this指向后不会立即执行,返回一个永久改变this指向的函数

三者的区别:

  • 三者都可以改变函数的this对象指向。
  • 三者第一个参数都是 this要指向的对象,如果如果没有这个参数或参数为undefined或null,则默认指向全局 window。(重点)
  • 三者都可以传参,但是apply是数组,而call和bind是参数列表,且apply和call是一次性传入参数,而bind可以分为多次传入。
  • bind 是返回绑定this之后的函数,便于稍后调用;apply 、call 则是立即执行,且 只临时改变一次this指向

使用:

var names = 'lisi';
var zs = {names:'zhangsan'};
function f(age){
    console.log(this.names+" is "+age);
}
f(23); // lisi is 23
// 将f函数中的this指向固定到对象zs上;
f.call(zs,32); // zhangsan is 32
f.apply(zs,[23]); // zhangsan is 23

两种应用情况

第一种:事件绑定中的this
<input type="button" value="按钮" onclick="clickFun()">
<script>
    function clickFun(){
        this // 此函数的运行环境在全局window对象下,因此this指向window;
    }
</script><input type="button" value="按钮" onclick="this">
<!-- 运行环境在节点对象中,因此this指向本节点对象 -->
  • 当事件触发时,属性值就会作为JS代码被执行,当前运行环境下没有clickFun函数,因此浏览器就需要跳出当前运行环境,在整个环境中寻找一个叫clickFun的函数并执行这个函数,所以函数内部的this就指向了全局对象window;
  • 如果不是一个函数调用,直接在当前节点对象环境下使用this,那么this就指向当前节点对象。
<input type="button" value="按钮" id="btn">
<script>
    var btn = document.getElementById('btn');
    btn.onclick = function(){
        this ;  // this指向本节点对象
    }
</script>
  • 为节点对象的属性重新赋值为一个匿名函数,因此函数在执行时就是在节点对象的环境下
第二种:window定时器中的this
var obj = {
    fun:function(){
        this ;
    }
}// setInterval():第一个参数是一个函数或者一段可执行的 JS 代码
setInterval(obj.fun,1000);      // this指向window对象
setInterval('obj.fun()',1000);  // this指向obj对象
  • 第一个参数obj.fun传递的是函数obj.fun()的地址,1000毫秒后,函数的运行环境是在Windows下,即this指向window对象
  • 第一个参数'obj.fun()'传入的一段可执行的 JS 代码,1000毫秒后,通过 obj 对象来找到 fun 函数并调用执行,那么函数的运行环境在对象 obj 内,即this指向obj对象

参考博客:JavaScript 的 this 原理Javascript 的 this 用法

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值