JavaScript学习总结--创建对象(5_还是原型)

这咋还没完没了呢?我们之前使用原型+构造函数混合模式创建对象时是这样子写的

function Person(name,age){
  this.name=name;
  this.age=age;
}
Person.prototype.sayName=function(){
   console.log(this.name);
}
var person1=new Person(‘Sakura‘,22);
person1.sayName();

很明显的一个问题就是,这段代码创建的对象似乎没有我们想象中那么完美,Person.prototype写在了构造函数外面,这样看起来很别扭,我们说封装,这咋没封到一块,咋还分道扬镳了?

那么我就想应该写成这样才对吧

function Person(name,age){
  this.name=name;
  this.age=age;
  Person.prototype.sayName=function(){
    console.log(this.name);
  }
}
var person1=new Person(‘Sakura‘,22);
person1.sayName();

是不是很完美,perfect对不对?

但是我们再来做一个实验

function Person(name,age){
  this.name=name;
  this.age=age;
  console.log(‘原型创建开始‘);
  Person.prototype.sayName=function(){
    console.log(this.name);
  }
  console.log(‘原型创建结束‘);
}
var person1=new Person(‘Sakura‘,22);
var person2=new Person(‘Misaka‘,20);

这段代码的意思是,每次实例化对象初始化原型对象之前都会在控制台输出一句话,创建完毕也会输出一句话,那么运行结果呢?

很明显这有问题啊,实例化了两个对象,然后这个原型被初始化了两次,这不是浪费吗,我们是不是应该在初始化原型对象前先确认一下原型中是否存在某个方法,如果存在就不再初始化,如果不存在然后再初始化原型?

所以这才是为师的完全体

function Person(name,age){
  this.name=name;
  this.age=age;
  if(typeof this.sayName !=‘function‘){
    console.log(‘原型创建开始‘);
    Person.prototype.sayName=function(){
      console.log(this.name);
    }
    console.log(‘原型创建结束‘);
  }
}
var person1=new Person(‘Sakura‘,22);
var person2=new Person(‘Misaka‘,20);

//原型创建开始
//原型创建结束

妥妥的,这种方法只需要if判断一次即可,也避免了原型重复初始化的问题,这叫做动态原型模式

不过有一点需要注意的是,使用动态原型模式时,不能使用对象字面量重写原型,因为在已经创建了实例的情况下,重写原型就会切断现有实例与新原型之间的联系

so,方法有很多种,选择适合自己的才好

我用五篇博文阐述了封装对象的几种常见方法(没看过的小伙伴可以往前翻一翻),本人也只是自学了几个月的初学者,如果文中有什么写的不对的地方欢迎留言指出,我会及时改正

我刻意的省去了一些专业术语(比如封装以及面向对象等),是为了避免初学者觉得过于晦涩难懂,也是为了让初学者看完觉得“哦,原来这就是面向对象的封装啊”,不至于被一些术语砸的晕头转向

文中的例子以及部分概念引用自《JavaScript高级程序设计》

另外封装对象还有两种较为少见的方法,将在后续博文中补全

时间: 2024-12-06 05:01:26

JavaScript学习总结--创建对象(5_还是原型)的相关文章

JavaScript学习总结--创建对象(3_原型)

当我们创建一个函数时,这个函数都会有一个prototype(原型)属性,这个属性是一个指针,指向一个对象,这个对象包含了特定类型的所有实例共享的属性和方法 就象这样 仔细观察我们可以发现,数组对象Array的prototype属性指向一个对象,而这个对象包含了很多属性和方法,其中就有我们常见的length属性,以及pop().push().shift()等方法 那么也就是说,这些属性和方法被定义在Array的prototype上,为所有的实例对象(数组)共享 所以我们在定义数组之后就可以使用这些

JavaScript学习总结(五)原型和原型链详解

转自:http://segmentfault.com/a/1190000000662547 私有变量和函数 在函数内部定义的变量和函数,如果不对外提供接口,外部是无法访问到的,也就是该函数的私有的变量和函数. <script type="text/javascript"> function Box(){ var color = "blue";//私有变量 var fn = function() //私有函数 { } } </script> 这

JavaScript学习总结--创建对象(2)

由于网络原因,所以写了一半就赶紧发了... 书接上回 既然工厂模式创建的对象不属于任何类型,我们知道JavaScript中实际上是没有类(class)这个概念的,所以我们需要创建一个伪类,这就用到了构造函数模式 2.构造函数模式 所谓构造函数,就是将工厂模式改写一下,使用new关键字,模仿JavaScript内置对象的形式来创建对象 我们知道JavaScript的内置对象(Array.Function等),创建时一般是 var aArr=new Array()的写法,且内置对象的首字母为大写,所

JavaScript学习笔记(三)——this、原型、javascript面向对象

一.this 在JavaScript中this表示:谁调用它,this就是谁. JavaScript是由对象组成的,一切皆为对象,万物皆为对象.this是一个动态的对象,根据调用的对象不同而发生变化,当然也可以使用call.apply修改this指向的对象.它代表函数运行时,自动生成的一个内部对象,只能在函数内部使用 1.1.JavaScript中函数与方法的区分 在面向过程的语言中我们习惯把完成某个特定功能的代码块称为“函数”或“过程”,当然过程一般没有返回值.在面向对象语言中我们把对象的功能

JavaScript学习总结(四)——this、原型链、javascript面向对象

一.this 在JavaScript中this表示:谁调用它,this就是谁. JavaScript是由对象组成的,一切皆为对象,万物皆为对象.this是一个动态的对象,根据调用的对象不同而发生变化,当然也可以使用call.apply修改this指向的对象.它代表函数运行时,自动生成的一个内部对象,只能在函数内部使用 1.0.猜猜答案 代码如下: <!DOCTYPE html> <html> <head> <meta charset="UTF-8&quo

JavaScript学习总结--创建对象(6_其他方法)

前面我们一共介绍了四种方法用来封装对象(工厂,构造模式,原型模式,构造+原型),并且重点对构造函数+原型模式做了一些改进,使之更加完美,那么除了这几种方法, 还有两种方式用来封装对象,还是那句话,选择适合自己的(其实每种方法都各有利弊,在我刚开始学习时总感觉就是拆东墙补西墙). 首先来看第一种方法 function Person(name,age){ var o=new Object(); o.name=name; o.age=age; o.sayName=function(){ console

JavaScript学习笔记-创建对象之设计模式

<!DOCTYPE html><html> <head>  <title>浏览器对象</title>    <meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>    </head> <body>    <script>         <!--创建对象之普通模式--&g

JavaScript学习总结--创建对象

ECMA-262定义的对象是:无序属性的集合,其属性可以包含基本值.对象或者函数 说白了就是把一组特定的变量和方法封装起来 那么我们先创建一个对象 var person=new Object(); person.name="Sakura"; person.age=22; person.job="前端开发"; person.sayName=function(){ console.log(this.name); } //当一个变量被封装在一个对象中时,这个变量就可以称为

javascript学习:闭包和prototype原型使用基础

闭包 function Person(name) { this.Username = name; var Userage = 18; //通过这种方法可以模拟私有成员 //类似于private成员 this.setAge = function (age) { Userage = age; } //类似于public成员 this.getAge = function () { return Userage; } } var p1 = new Person("huahuah"); p1.s