资讯专栏INFORMATION COLUMN

没有对象?new一个!

DataPipeline / 1005人阅读

摘要:这是为什么呢原因是构造函数中的并没有指向当前的新对象,此时方法就可完美解决这个问题方法也可,具体的的使用及与的异同可参照大神文章。

我们都知道,使用new后可返回一个对象,通常用于实例化一个“类”。
用法:

function Student (name, age) {
    this.name = name;
    this.age = age;
}
Student.prototype.sayName = function() {
    console.log("I am "+ this.name);
}
const person =new Student("小明");
person.sayName();  // I am 小明
问题分析

首先我们分析一下,手动实现new需要什么。

创建一个函数,可返回一个新的对象

需要访问到Student构造函数里的属性

需要访问到Student.prototype中的属性和方法

具体步骤分析 一、参数传递

若要实现上面代码的相同效果,首先明确需要一个“类”的参数,以及其它参数(如name)。
js 的函数参数非常灵活,形参数量可不确定(使用...args),也可不给出。函数中有一个 与生俱来的arguments对象,具有length属性,但不是数组,所以不可使用数组方法。

arguments 简单分析

下述代码中的输出语句结果即为所传实参的集合:

{ "0": [Function: Student], "1": "小明", "2": 18 }

function objectFactory() {
    console.log(arguments);
}
const person = objectFactory(Student, "小明",18);
二、方法实现 1.得到 Student 类的构造函数

由前面 arguments 简单分析可知,arguments中的第一个参数即为Student的构造函数。上面说到,arguments 并非数组,那我们如何得到第一项呢?

两种方法:[].shift.call(arguments)Array.from(arguments)

var Constructor = [].shift.call(arguments);
2.创建一个新的对象

创建一个新的对象非常简单,如下:

const obj = new Object();
3.设置新对象的 __proto__ 属性

__proto__是对象的私有属性,指向构造该对象的构造函数的原型。所以此步须将新的对象的此属性指向 Constructor的原型。

obj.__proto__ = Constructor.prototype;
4.得到构造函数上的 this 属性

若要实例化一个“类”,则必须调用其构造函数,在执行构造函数时,其 this的值是动态的变化的,即为当前调用该函数的对象。

可是这里有个问题,若此时直接调用构造函数并传值

Constructor(arguments);

最终结果将为undefined

这是为什么呢?

原因是构造函数中的 this并没有指向当前的新对象,此时apply()方法就可完美解决这个问题(call()方法也可),具体的apply()的使用及apply()call()的异同可参照大神文章。

结果:

function objectFactory(){
    var Constructor = [].shift.call(arguments);
    var obj = new Object();
    obj.__proto__ = Constructor.prototype;
    Constructor.apply(obj, arguments);
    return obj;
}

const person = objectFactory(Student, "小明", 18);
person.sayName();   // I am 小明
结束

对于手动实现new的学习,原型的概念更清晰了,在具体的实现过程中也学习到了shiftcallapply等方法的一些使用。收获颇丰。

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

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

相关文章

  • JavaScript 工厂函数 vs 构造函数

    摘要:当谈到语言与其他编程语言相比时,你可能会听到一些令人困惑东西,其中之一是工厂函数和构造函数。好的,让我们用构造函数做同样的实验。当我们使用工厂函数创建对象时,它的指向,而当从构造函数创建对象时,它指向它的构造函数原型对象。 showImg(https://segmentfault.com/img/bVbr58T?w=1600&h=900); 当谈到JavaScript语言与其他编程语言...

    RayKr 评论0 收藏0
  • javascript创建对象

    摘要:就是通过调用构造函数而创建的那个对象实例的原型对象。与寄生构造函数模式类似,使用稳妥构造函数模式创建的对象与构造函数之间也没有什么关系,因此操作符对这种对象也没有什么意义 虽然Object构造函数或对象字面量都可以用来创建单个对象,但是这些方法有明显的缺点:使用同一个接口创建很多对象,会产生大量重复代码。因此人们开始使用工厂模式。 工厂模式 这种模式抽象了创建具体对象的过程 funct...

    Keven 评论0 收藏0
  • 面向对象的小九九

    摘要:由构造函数返回的对象就是表达式的结果。如果构造函数没有显式返回一个对象,则使用步骤创建的对象。运算符返回一个布尔值,表示对象是否为某个构造函数的实例。 面向对象 本人能力有限,有误请斧正 本文旨在复习面向对象(不包含es6) 本文学习思维 创建对象的方式,获取对象属性 构造函数,构造函数的new 做了什么 原型与原型对象 原型链 继承(借用构造继承、原型继承、组合继承、寄生组合继承)...

    时飞 评论0 收藏0
  • 理解js对象

    摘要:将构造函数的作用域赋值给新对象因此指向了新对象执行构造函数的代码为这个新对象添加属性返回对象最初是用来标识对象类型的。但提到检测对象类型,还是使用将构造函数当作函数构造函数与其他函数唯一区别。 创建对象 虽然Object构造函数与对象字面量都能创建单个对象, 但这些方式都有明显的缺点: 使用同一个接口创建很多对象, 会产生大量重复代码。 var obj = {}; //对象字面量 va...

    zhouzhou 评论0 收藏0
  • 【9】JavaScript 面向对象高级——对象创建模式

    摘要:解决了构造函数模式不能共享方法的问题。六寄生构造模式流程创建一个构造函数,在这个函数内部创建一个对象,用返回对象。除了使用操作符并把使用的包装函数叫做构造函数以外,这个模式与工程模式其实是一模一样的。 JavaScript面向对象高级——对象创建模式 一、工厂模式 流程: 定义一个函数,函数返回对象。 适用场景: 需要创建多个对象,都是Object类型。 优点:完成了返回一个对象的...

    linkin 评论0 收藏0
  • Java引用类型分析

    摘要:强引用是使用最普遍的引用,它是默认的引用类型,不需要显式声明,在中没有实际的类对应,可以把它理解为的内置省略默认引用类型。相同点当执行时,两者引用的对象都会被回收。这时已经无法获得引用的对象,并且对象被放入了。 概述 java.lang.ref 类库包含一组类,为垃圾回收提供了更大的灵活性。 java.lang.ref 有三个继承自抽象类 Reference 的类: showImg(h...

    wyk1184 评论0 收藏0

发表评论

0条评论

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