资讯专栏INFORMATION COLUMN

深究JavaScript——函数调用与this详解

PiscesYE / 1646人阅读

摘要:构造器的目的是要创建一个新对象并对其进行设置,然后将其作为构造器的返回值进行返回,是通过函数调用初始化创建新对象。或方法进行调用通过或调用函数,被调用的函数的指向第一个参数指向的。

this

  JavaScript的this总是指向一个对象,而这个对象是基于函数运行时动态绑定的,并非函数声明时绑定。

函数调用方式

作为对象的方法调用

作为普通函数进行调用

作为构造器进行调用

通过apply()或call()方法进行调用

函数参数

  所有函数调用都会传递两个隐式参数:arguments和this。
  所谓隐式,也就意味着这些参数不会显示列在函数签名里,但是它们默默地传递给函数并存在于函数作用域内。在函数内部,它们可以像其他显式命名的参数一样使用。

arguments参数

  arguments参数是传递给函数的所有参数的一个集合。该集合有一个length属性,其值是全部参数的个数,单个参数值可以像访问数组索引一样进行获取。
  但要避免将arguments参数作为数组进行调用。可以利用Array.prototype.slice.call(arguments, 0)将arguments参数转换为数组;

this参数

  this参数引用了与该函数调用进行隐式关联的一个对象,被称之为函数上下文。

this指向 作为对象方法进行调用

  当函数作为对象的方法被调用时,this指向该对象。该对象就成了函数上下文。

window.name = "global";

var obj = {
    name: "staven",
    getName: function () {
        return this.name;
    }
};
//作为对象方法调用
console.log(obj.getName());   //staven
作为普通函数进行调用

  一种方式调用,函数的上下文时全局上下文——window对象。

window.name = "global";

var obj = {
    name: "staven",
    getName: function () {
        return this.name;
    }
};
//作为对象方法调用
console.log(obj.getName());   //staven
//将函数引用指针赋给getName变量
var getName = obj.getName;
//作为普通函数调用
console.log(getName());   //global

  常见的一种情形是,函数中的某个函数内部的this指向的是全局对象。解决这种问题,可var that = this;内部函数使用that代替this。

作为构造器进行调用

  将函数作为构造器进行调用,我们要在函数调用前使用new关键字。其上下文是新创建的对象实例。
  构造器调用时,如下特殊行为会发生:

创建一个新的空对象

传递给构造器的对象是this参数,从而成为构造器的函数上下文。

如果没有显式的返回值,新创建的对象则作为构造器的返回值进行返回。

  构造器的目的是要创建一个新对象并对其进行设置,然后将其作为构造器的返回值进行返回,是通过函数调用初始化创建新对象。

var Person = function () {
    this.name = "staven";
};

var obj = new Person();
console.log(obj.name);  //staven

  如果构造器显式返回了一个对象,那么此次运算最终返回这个对象,而不是this。

var Person = function () {
    this.name = "staven";
    return {
        name: "backedName"
    }
};

var obj = new Person();
console.log(obj.name);  //backedName

  如果构造器不显式返回任何数据,或返回的非对象数据,就不会存在上述问题。

var Person = function () {
    this.name = "staven";
    return "backedName";
};

var obj = new Person();
console.log(obj.name);  //staven
apply()或call()方法进行调用

  通过call或apply调用函数,被调用的函数的this指向第一个参数指向的this。上下文可设为任意值。每个函数都有apply()和call()方法,使用其中一个方法,都可以显示指定任何一个对象作为其函数上下文。
  通过函数的apply()方法来调用函数,我们要给apply()传入两个参数:一个是作为函数上下文的对象,另外一个是作为函数参数所组成的数组。call()方法的使用方式类似,唯一不同的是,给函数传入的参数是一个参数列表,而不是单个数组。
  当使用 call 或者 apply 的时候,如果我们传入的第一个参数为null,函数体内的 this 会指向默认的宿主对象。

var obj1 = {
    name: "jsor",
    getName: function () {
        return this.name;
    }
};

var obj2 = {
    name: "staven"
};

console.log(obj1.getName());        //jsor
console.log(obj1.getName.call(obj2));   //staven

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/86695.html

相关文章

  • 深究JavaScript——执行上下文

    摘要:一系列活动的执行上下文从逻辑上形成一个栈。堆栈中的上下文就会被依次执行并且弹出堆栈,直到回到全局的上下文。确定上下文中的指向对象确定指向或当前对象。 定义 执行上下文(也称执行环境execution context)(简称:EC)是个抽象的概念,是在函数被调用时,但是在函数体被真正执行以前所创建的。每个执行上下文都有一个变量对象(variable object),保存着当前环境中所有的...

    netScorpion 评论0 收藏0
  • 深究JavaScript——闭包

    摘要:函数是中唯一拥有自身作用域的结构,因此闭包的创建依赖于函数。闭包中的匿名函数的执行环境具有全局性,因此其对象通常指向在通过或改变函数执行环境的情况下,就会指向其他对象。当匿名函数执行完毕,其作用域链立即销毁,从而可以减少闭包占用资源问题。 概念   闭包是指能够引用外部函数中的局部变量的函数,并导致外部函数调用后函数对象与局部变量无法及时销毁。函数是JavaScript中唯一拥有自身作...

    Dionysus_go 评论0 收藏0
  • 深究JavaScript——原型:prototype、constructor、__proto__

    摘要:是构造函数的属性,而不是实例对象的属性,指向原型对象。这个连接存在于实例与构造函数的原型对象而不是构造函数之间,也就是说实例对象与构造函数没有直接关系。 prototype、constructor、__proto__   prototype是站在构造函数的角度讨论原型对象的,用来实现基于原型的继承与属性的共享。__proto__是站在实例对象的角度讨论原型对象,构成原型链,同样用于实现...

    jeffrey_up 评论0 收藏0
  • 深究JavaScript——参数传递变量复制

    摘要:在操作对象时,实际上是在操作对象的引用而不是实际的对象。任一变量值操作互不影响。访问变量有按值和按引用两种方式,而参数只能按值传递。基本类型参数传递传给函数的是数值的一个复制,函数中对其的修改外部不可见。    ECMAScript 变量可能包含两种不同数据类型的值:基本类型值和引用类型值。 基本类型值指的是简单的数据段,而引用类型值指那些可能由多个值构成的对象。   5 种基本数据类...

    jzman 评论0 收藏0
  • JavaScript深入浅出

    摘要:理解的函数基础要搞好深入浅出原型使用原型模型,虽然这经常被当作缺点提及,但是只要善于运用,其实基于原型的继承模型比传统的类继承还要强大。中文指南基本操作指南二继续熟悉的几对方法,包括,,。商业转载请联系作者获得授权,非商业转载请注明出处。 怎样使用 this 因为本人属于伪前端,因此文中只看懂了 8 成左右,希望能够给大家带来帮助....(据说是阿里的前端妹子写的) this 的值到底...

    blair 评论0 收藏0

发表评论

0条评论

PiscesYE

|高级讲师

TA的文章

阅读更多
最新活动
阅读需要支付1元查看
<