Loading [MathJax]/jax/input/TeX/config.js
前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >javascript 面向对象(多种创建对象的方式)

javascript 面向对象(多种创建对象的方式)

作者头像
柴小智
发布于 2018-04-10 09:20:11
发布于 2018-04-10 09:20:11
98900
代码可运行
举报
文章被收录于专栏:菜鸟计划菜鸟计划
运行总次数:0
代码可运行

创建对象

第一种:基于Object对象

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
var person = new Object();
person.name = 'My Name';
person.age = 18;
person.getName = function(){
    return this.name;
}

第二种:对象字面量方式(比较清楚的查找对象包含的属性及方法)

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
var person = {
    name : 'My name',
    age : 18,
    getName : function(){
        return this.name;
    }
}

使用Object构造函数或对象字面量都可以创建对象,但缺点是创建多个对象时,会产生大量的重复代码,因此下面介绍可解决这个问题的创建对象的方法

1、工厂模式
代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
function createPerson(name, age) {
    var o = new Object();
    o.name = name;
    o.age = age;
    o.getAge = function () {
        return this.age;
    };
    return o;
}
var person = createPerson('张三', 23);  
console.log(person.name);     //'张三'
console.log(person.age);    //23
console.log(person.getAge());  //23

 缺点:创建对象交给一个工厂方法来实现,可以传递参数,但主要缺点是无法识别对象类型,因为创建对象都是使用Object的原生构造函数来完成的。

2、构造函数模式
代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
function Person(name, age) {
    this.name = name;
    this.age = age;
    this.getAge = function () {
        return this.age;
    };
}
var person = new Person('张三', 23);
console.log(person.name);  //'张三'
console.log(person.age);   //23
console.log(person.getAge());  //23

 2.1 使用自定义的构造函数(与普通函数一样,只是用它来创建对象),定义对象类型(如:Person)的属性和方法。它与工厂方法区别在于:

  • 没有显式地创建对象
  • 直接将属性和方法赋值给this对象;
  • 没有return语句;

此外,要创建Person的实例,必须使用new关键字,以Person函数为构造函数,传递参数完成对象创建;

2.2 要创建 Person 的新实例,必须使用 new 操作符。以这种方式调用构造函数实际上会经历以下 4个步骤:

(1) 创建一个新对象; (2) 将构造函数的作用域赋给新对象(因此 this 就指向了这个新对象); (3) 执行构造函数中的代码(为这个新对象添加属性); (4) 返回新对象。

在前面例子的最后, person1 和 person2 分别保存着 Person 的一个不同的实例。这两个对象都有一个 constructor (构造函数)属性,该属性指向 Person ,如下所示。 alert(person1.constructor == Person); //true alert(person2.constructor == Person); //true

对象的 constructor 属性最初是用来标识对象类型的。

创建自定义的构造函数意味着将来可以将它的实例标识为一种特定的类型;而这正是构造函数模式胜过工厂模式的地方。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
function Person(name, age) {
    this.name = name;
    this.age = age;
    this.getAge =  new Function ("return this.age");  //和上面是一样的,会重复创建多个函数
}

缺点:上述代码,创建多个实例时,会重复调用new Function();创建多个函数实例,这些函数实例还不是一个作用域中,当然这一般不会有错,但这会造成内存浪费。

3、原型模式
代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
function Person(name) {
    this.name = name;
}
Person.prototype.age = 23;
Person.prototype.getAge = function () {
    return this.age;
};
var person = new Person('张三');
console.log(person.name);  //'张三'
console.log(person.age);  //23
console.log(person.getAge());  //23

JS每个函数都有一个prototype(原型)属性,这个属性是一个指针,指向一个对象,它是所有通过new操作符使用函数创建的实例的原型对象。

原型对象最大特点是,所有对象实例共享它所包含的属性和方法,也就是说,所有在原型对象中创建的属性或方法都直接被所有对象实例共享。

 实例属性或方法的访问过程是一次搜索过程:

  • 首先从对象实例本身开始,如果找到属性就直接返回该属性值;
  • 如果实例本身不存在要查找属性,就继续搜索指针指向的原型对象,在其中查找给定名字的属性,如果有就返回;

基于以上分析,原型模式创建的对象实例,其属性是共享原型对象的;但也可以自己实例中再进行定义,在查找时,就不从原型对象获取,而是根据搜索原则,得到本实例的返回;简单来说,就是实例中属性会屏蔽原型对象中的属性;

可以通过使用hasOwnProperty()方法来判断,属性是实例本身的,还是原型上的。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
person.hasOwnProperty("name");    //true        
person.hasOwnProperty("age");       //false

 缺点:最主要是当对象的属性是引用类型时,它的值是不变的,总是引用同一个外部对象,所有实例对该对象任何一个地方产生的改动会引起其他实例的变化。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
function Person(name) {
    this.name = name;
}
Person.prototype.age = 23;
Person.prototype.color = ['red', 'yellow']; 
var person1 = new Person('张三');
console.log(person1.name);  //'张三'
console.log(person1.color);  //["red", "yellow"]
person1.color.push('black');  
var person2 = new Person('李四');
console.log(person2.name);  //'李四'
console.log(person2.color);  //["red", "yellow", "black"]  //person1的修改影响了person2
4、组合使用构造函数模式及原型模式

目前最为常用的定义类型方式,是组合使用构造函数模式与原型模式。

构造函数模式用于定义实例的属性,而原型模式用于定义方法和共享的属性。结果,每个实例都会有自己的一份实例属性的副本,但同时又共享着对方方法的引用,最大限度的节约内存。

此外,组合模式还支持向构造函数传递参数,可谓是集两家之所长。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
function Person(name, age) {
    this.name = name;
    this.age = age;
    this.color = ['red', 'yellow'];
}
Person.prototype = {
    constructor : Person,  //原型字面量形式会将对象的constructor变Object,此外强制指回Person;
    getAge : function () {
        return this.age;
    }
};
var person1 = new Person('张三', 23);
person1.color.push('black');
console.log(person1.name);  //张三
console.log(person1.color);  //["red", "yellow", "black"]
console.log(person1.getAge());  //23
var person2 = new Person('李四', 24);
console.log(person2.name);  //李四
console.log(person2.color);  //['red','yellow']  
console.log(person2.getAge());  //24
 5、动态原型模式

     组合模式中实例属性与共享方法(由原型定义)是分离的,这与纯面向对象语言不太一致;动态原型模式将所有构造信息都封装在构造函数中,又保持了组合的优点。其原理就是通过判断构造函数的原型中是否已经定义了共享的方法或属性,如果没有则定义,否则不再执行定义过程。该方式只原型上方法或属性只定义一次,且将所有构造过程都封装在构造函数中,对原型所做的修改能立即体现所有实例中:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
function Person(name, age, job) {
    this.name = name;
    this.age = age;
    this.job = job;
    this.lessons = ['Math', 'Physics'];
}
if (typeof this.getName != 'function') {//通过判断实例封装
  Person.prototype = {
    constructor: Person,//原型字面量方式会将对象的constructor变为Object,此外强制指回Person
    getName: function () {
      return this.name;
    }
  }
}
var person1 = new Person('Jack', 19, 'SoftWare Engneer');
person1.lessons.push('Biology');
var person2 = new Person('Lily', 39, 'Mechanical Engneer');
alert(person1.lessons);//Math,Physics,Biology
alert(person2.lessons);//Math,Physics
alert(person1.getName === person2.getName);//true,//共享原型中定义方法
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2018-03-04 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
JavaScript面向对象程序设计—创建对象的模式
JS本身为我们提供了Array、Date、Math等不少对象(见《浅析JavaScript的对象系统》),但在实际开发中我们使用最多的还是自定义对象。自定义对象是一门值得研究的学问。往浅了讲,它关系到代码量、封装性、代码是否优雅;往深了讲,它又涉及到内存开销、设计模式乃至JavaScript语言的核心。下面就一起循序渐进地看看如何更好地创建一个对象。 1. 基本模式 ---- var person = new Object(); //或 var person = {};person.name = "
用户1667431
2018/04/18
9500
Javascript之创建对象
Object构造函数 创建自定义对象最简单的方式就是创建一个 Object 的实例,然后再为它添加属性和方法: // 创建对象 var person = new Object(); // 定义属性 person.name = 'laixiangran'; person.age = 28; person.job = 'Front End Software Engineer'; // 定义方法 person.sayName = function() { console.log(this.name);
laixiangran
2018/04/11
8530
深入理解JavaScript面向对象的程序设计(一)——对象的创建
类似Java等面向对象语言中创建对象的语法,在 JavaScript中可以通过执行 new操作符后跟要创建的对象类型的名称来创建。JavaScript中通过如下方式可以创建一个Object对象:
CherishTheYouth
2020/11/12
4430
深入理解JavaScript面向对象的程序设计(一)——对象的创建
JavaScript中创建对象的多种方式和优缺点
要创建 Person 的实例,需使用 new 操作符。用 new 操作符创建实例大约会执行一下几个步骤:
andyhu
2023/06/10
2970
JavaScript之面向对象学习一
1、通过Object构造函数和对象字面量来创建对象缺点:使用同一个接口创建很多的对象,会产生大量的重复代码。比如我需要创建人的对象,并且需要三类人,医生、工程师、老师,他们可以抽象出很多属性,比如姓名、年龄、工作等,只是各自的值不一样,如果这里我用Object或者对象字面量来创建的话,那我必须每个人都写一次这三个属性,造成了代码重复。 2、思考下方法一的问题,我们发现我们可以通过一个工厂来创建对象,这样做的好处是,我们能把一些共同的属性封装到工厂里面,而我们创建对象时,只需要把对象的参数,传递给工厂函数,在
郑小超.
2018/01/24
5000
JavaScript之面向对象学习一
浅谈JavaScript的面向对象程序设计(二)
  前面介绍通过Object构造函数或者字面量创建单个对象,但是通过这个的方法创建对象有明显的缺点:调用同一个接口创建多个实例,会产生大量的重复代码。怎么样解决? 工厂模式 工厂模式是软件工程领域经常使用的一种设计模式,这种设计模式抽象了创建对象的具体过程。由于在JavaScript中无法使用类,可以使用函数来封装特定接口创建对象。 1 function createPerson(name,age,sex){ 2 var obj= new Object();
水击三千
2018/02/27
5690
JavaScript中创建对象的几种模式
代码如下: 1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="UTF-8"> 5 <title>创建对象的模式</title> 6 <meta name="viewport" content="width=device-width, initial-scale=1"> 7 <!--<link rel="stylesheet" type="text/css" href="ma
用户1149564
2018/07/31
1.3K0
JavaScript中创建对象的几种模式
JavaScript创建对象的7种模式
1)工厂模式 这种模式抽象了创建具体对象的过程 考虑到在 ECMAScript 中无法创建类,开发人员就发明了一种函数,用函数来封装以特定接口创建对象的细节 function createPerson(name, age, job){ var o = new Object(); o.name = name; o.age = age; o.job = job; o.sayName = function(){ alert(this.name); }; return o;}var person1 = creat
用户1667431
2018/04/18
8070
JavaScript创建对象的7种模式
JavaScript之面向对象学习六原型模式创建对象的问题,组合使用构造函数模式和原型模式创建对象
一、仔细分析前面的原型模式创建对象的方法,发现原型模式创建对象,也存在一些问题,如下: 1、它省略了为构造函数传递初始化参数这个环节,结果所有实例在默认的情况下都将取得相同的属性值,这还不是最大的问题! 2、最大的问题是原型中的所有属性是被很多实例所共享的,这种共享对于函数非常合适,对于那些包含基本值的属性也说得过去,因为我们知道可以在实例上添加一个同名属性,可以隐藏原型中的对应属性。但是对于包含应用类型值的属性来说,问题就非常严重了,代码如下: function Person(){ } Person.pr
郑小超.
2018/01/24
1.4K0
JavaScript的几种创建对象的方式
除了使用 new 操作符并把 使用的包装函数叫做构造函数之外,这个模式跟工厂模式其实是一模一样的。
木子星兮
2020/07/16
4970
JavaScript面向对象的程序设计
工厂模式 由于 ES6 之前没有 class 概念,所以使用函数来封装的,工程模式采用最直接的传入参数创建对象并赋值,然后返回对象的方式 function Great(name,age) { var o = new Object(); o.name = name; o.age = age; o.getName = function() { return this.name; } return o; } var g1 = Great('link',21); consol
努力的Greatiga
2022/07/25
2580
浅谈JavaScript的面向对象程序设计(三)
  前面已经对JavaScript的面向对象程序设计作了简单的介绍,包括了对象的属性、对象的工厂模式、构造函数和原型等。通过介绍,这些创建对象的方法依然有不少优化和改进的地方。 组合使用构造函数模式和原型模式   创建自定义类型的最常用方式就是使用组合构造函数和原型模式。构造函数用于定义实例属性,原型用于定义共享的属性和方法。每个实例都有自己的实例副本,同时又共享了原型属性和方法,节省了内存。还支持向函数传递参数。 1 function Person(name,age,sex){ 2
水击三千
2018/02/27
5520
javaScript 的面向对象程序
数据属性(数据属性包含一个数据值的位置,这个位置可以读取和写入值,数据属性有4描述)
用户1197315
2019/12/30
1.1K0
JavaScript 进阶教程(1)--面向对象编程
一本书、一辆汽车、一个人都可以是对象,一个数据库、一张网页、一个与远程服务器的连接也可以是对象。当实物被抽象成对象,实物之间的关系就变成了对象之间的关系,从而就可以模拟现实情况,针对对象进行编程。
AlbertYang
2020/09/08
5190
JavaScript 进阶教程(1)--面向对象编程
JS面向对象的程序设计
http://www.cnblogs.com/gaojun/p/3386552.html
bear_fish
2018/09/19
1.3K0
js程序设计03——面向对象
ECMAScript中有2中属性:数据属性、访问器属性。 数据属性是为了指定某对象的指定key上的一些行为,比如value是否可删除、修改、key可循环遍历等特点。而访问器属性不包含数据值,包含一堆g
用户1141560
2017/12/26
1.2K0
js程序设计03——面向对象
JS篇(009)-javascript 对象的几种创建方式
这行代码创建了 Object 引用类型的一个新实例,然后把实例保存在变量 Person 中。 第二种:使用对象字面量表示法
齐丶先丶森
2022/05/12
1.7K0
JS中的面向对象、原型、原型链、继承总结大全
补充: js中说一切都是对象,是不完全的,在js中6种数据类型(Undefined,Null,Number,Boolean,String,Object)中,前五种是基本数据类型,是原始值类型,这些值是在底层实现的,他们不是object,所以没有原型,没有构造函数,所以并不是像创建对象那样通过构造函数创建的实例。关于对象属性类型的介绍就不介绍了。
疯狂的技术宅
2019/03/27
1.4K0
JS中的面向对象、原型、原型链、继承总结大全
【说站】javascript创建对象的方法
1、构造函数模式,没有显示创建对象,直接将属性方法赋给this,没有return语句。
很酷的站长
2022/11/24
4740
【说站】javascript创建对象的方法
面向对象编程
面向对象把构成问题的transaction分解成各个对象,而建立对象的目的也不是为了完成一个个步骤,而是为了描述某个事物在解决整个问题的过程中所发生的行为,意在写出通用代码,加强代码重用,屏蔽差异性。
子舒
2022/06/09
7050
面向对象编程
推荐阅读
相关推荐
JavaScript面向对象程序设计—创建对象的模式
更多 >
领券
💥开发者 MCP广场重磅上线!
精选全网热门MCP server,让你的AI更好用 🚀
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
本文部分代码块支持一键运行,欢迎体验
本文部分代码块支持一键运行,欢迎体验