最初对js中 object.constructor 的认识:

在学习JS的面向对象过程中,一直对constructor与prototype感到很迷惑,看了一些博客与书籍,觉得自己弄明白了,现在记录如下:

我们都知道,在JS中有一个function的东西。一般人们叫它函数。比如下面的代码

function Person(name)   
{   
  alert(name);   
}   
Person('js');//js  

上面的代码中,Person的表现的确跟一般的函数没有什么区别,接着看下面的代码

 

function Person(name)   
{   
   this.name=name;   
   this.showMe=function()   
        {   
           alert(this.name);   
        }   
};   
var one=new Person('JavaScript');   
one.showMe();//JavaScript    

很多人见到了久违的new操作符,于是就叫Person为“类”,可是又没有关键字class的出现,觉得叫“类”有点勉强。于是退而求其次叫Person为类的构造函数。这些概念好像都没有错,之所以出现这样的情况,可能是因为大家都学习了传统的面向对象语言(c++,c#,java等),还有一种思维定势吧。为了让javascript也面向对象,要在javascript中找到与传统面向对象语言的影子。可是按照javascript的说法,function定义的这个Person就是一个Object(对象),而且还是一个很特殊的对象,这个使用function定义的对象与使用new操作符生成的对象之间有一个重要的区别。这个区别就是function定义的对象有一个prototype属性,使用new生成的对象就没有这个prototype属性

prototype属性又指向了一个prototype对象,注意prototype属性prototype对象是两个不同的东西,要注意区别。在prototype对象中又有一个constructor属性,这个constructor属性同样指向一个constructor对象,而这个constructor对象恰恰就是这个function函数本身。

有点头晕,看下图吧:

不相信可以看下面的代码:


function Person(name)   
{   
   this.name=name;   
   this.showMe=function()   
        {   
           alert(this.name);   
        }   
};   
  
var one=new Person('js');   
  
alert(one.prototype)//undefined   
alert(typeof Person.prototype);//object   
alert(Person.prototype.constructor);//function Person(name) {...};    

上面的代码证明了one这个对象没有prototype属性。

我们接着看代码:

function Person(name)   

{   
   this.name=name;   
   this.showMe=function()   
        {   
           alert(this.name);   
        }   
};   
  
Person.prototype.from=function()   
{   
  alert('I come from prototype.');   
}   
  
var one=new Person('js');   
  
one.showMe();//js,这个结果没有什么好奇怪的   
one.from();//I come from prototype.,这个结果有一点奇怪吧    

要解释这个结果就要仔细研究一下new这个操作符了.var one=new Person('js');这个语句执行的过程可以分成下面的语句:

var one={};   
Person.call(one,'js');  

按照《悟透javascript》书中说的,new形式创建对象的过程实际上可以分为三步:

第一步是建立一个新对象(叫A吧);

第二步将该对象(A)内置的原型对象设置为构造函数(就是Person)prototype 属性引用的那个原型对象;

第三步就是将该对象(A)作为this 参数调用构造函数(就是Person),完成成员设置等初始化工作。

其中第二步中出现了一个新名词就是内置的原型对象,注意这个新名词跟prototype对象不是一回事,为了区别我叫它inobj,inobj就指向了函数Person的prototype对象。在person的prototype对象中出现的任何属性或者函数都可以在one对象中直接使用,这个就是javascript中的原型继承了

又头晕了,上图吧!

这样one对象通过内置的原型对象inobj就可以直接访问Person的prototype对象中的任何属性与方法了。这也就解释了上面的代码中为什么one可以访问form函数了。因为prototype对象中有一个constructor属性,那么one也可以直接访问constructor属性。

function Person(name)   

{   
   this.name=name;   
   this.showMe=function()   
        {   
           alert(this.name);   
        }   
};   
  
Person.prototype.from=function()   
{   
  alert('I come from prototype.');   
}   
  
var one=new Person('js');   
  
one.showMe();//js,这个结果没有什么好奇怪的   
one.from();//I come from prototype.,这个结果有一点奇怪吧   
alert(one.constructor);//function Person(name) {...}   
alert(Person.prototype.constructor);//function Person(name) {...}  

接着看继承是如何实现的。


function Person(name)   
{   
   this.name=name;   
   this.showMe=function()   
        {   
           alert(this.name);   
        }   
};   
  
Person.prototype.from=function()   
{   
  alert('I come from prototype.');   
}   
  
function SubPerson()   
{   
}   
SubPerson.prototype=new Person();   
  
var subOne=new SubPerson();   
subOne.from();//I come from prototype.   
alert(subOne.constructor);//function Person(name) {...};   
alert(SubPerson.prototype.constructor);//function Person(name) {...};    

继承的实现很简单,只需要把子类的prototype设置为父类的一个(实例化)对象即可。注意这里说的可是对象哦!

那么通过prototype属性实现继承的原理是什么呢?还是先看图形说明,然后编写代码进行验证。

注意:红色的方框就是把子类与父类链接起来的地方。这个就应该是传说中的prototype链了吧。下面有代码进行验证。

 
function Person(name)   
{   
   this.name=name;   
   this.showMe=function()   
        {   
           alert(this.name);   
        }   
};   
  
Person.prototype.from=function()   
{   
  alert('I come from prototype.');   
}   
var father=new Person('js');//为了下面演示使用showMe方法,采用了js参数,实际多采用无参数   
alert(father.constructor);//查看构造函数,结果是:function Person(name) {...};   
function SubPer()   
{   
}   
SubPer.prototype=father;//注意这里   
SubPer.prototype.constructor=SubPer;   
  
var son=new SubPer();   
son.showMe();//js   
son.from();//I come from prototype.   
alert(father.constructor);//function SubPer(){...}   
alert(son.constructor);//function SubPer(){...}   
alert(SubPer.prototype.constructor);//function SubPer(){...}  

根据上图的prototype链,还有代码的结果,我想应该明白为什么使用prototype能够实现

JS中的继承了吧。

参考:http://blog.csdn.net/niuyongjie/archive/2009/11/15/4810835.aspx

【转】JavaScript中的constructor与prototype的更多相关文章

  1. 分析js中的constructor 和prototype

    在javascript的使用过程中,constructor 和prototype这两个概念是相当重要的,深入的理解这两个概念对理解js的一些核心概念非常的重要. 我们在定义函数的时候,函数定义的时候函 ...

  2. 深入分析js中的constructor 和prototype

    在javascript的使用过程中,constructor 和prototype这两个概念是相当重要的,深入的理解这两个概念对理解js的一些核心概念非常的重要. 我们在定义函数的时候,函数定义的时候函 ...

  3. 深入浅析JavaScript中的constructor

    constructor 属性返回对创建此对象的数组函数的引用.本文给大家介绍JavaScript中的constructor ,需要的朋友参考下吧 定义和用法 constructor 属性返回对创建此对 ...

  4. 深入了解JavaScript中基于原型(prototype)的继承机制

    原型 前言 继承是面向对象编程中相当重要的一个概念,它对帮助代码复用起到了很大的作用. 正文 Brendan Eich在创建JavaScript时,没有选择当时最流行的类继承机制,而是借鉴Self,用 ...

  5. 【JavaScript】关于JS中的constructor与prototype

    最初对js中 object.constructor 的认识: 在学习JS的面向对象过程中,一直对constructor与prototype感到很迷惑,看了一些博客与书籍,觉得自己弄明白了,现在记录如下 ...

  6. Javascript中的__proto__、prototype、constructor

    今天重温了下Javacript,给大家带来一篇Javascript博文,相信对于Javacript有一定了解的人都听过prototype原型这个概念,今天我们深度的分析下prototype与__pro ...

  7. 彻底搞清javascript中this, constructor, prototype

    说起这三个属性,肯定有一些同学和我一样,初学js时非常困惑,头大,一脸的迷茫.今天就来给大家彻底解决这些担心受怕的问题. 先看this this定义: this就是函数赖以执行的对象. 分析这句话: ...

  8. JavaScript——this、constructor、prototype

    this this表示当前对象,如果在全局作用范围内使用this,则指代当前页面对象window: 如果在函数中使用this,则this指代什么是根据运行时此函数在什么对象上被调用. 我们还可以使用a ...

  9. JS中的constructor与prototype

    http://www.cnblogs.com/qiantuwuliang/archive/2011/01/08/1930548.html 在学习JS的面向对象过程中,一直对constructor与pr ...

随机推荐

  1. leetcode面试准备:Contains Duplicate I && II

    1 题目 Contains Duplicate I Given an array of integers, find if the array contains any duplicates. You ...

  2. 项目属性-->生成事件-->后期生成事件命令行

    以开源记牌器https://github.com/Epix37/Hearthstone-Deck-Tracker 为例,Hearthstone Deck Tracker项目中的后期生成事件命令行: i ...

  3. SQL Server 2008 R2 制作数据库结构和数据脚本

    数据库中包含众多表和数据,有时候需要创建脚本将表结构和数据一起导出 具体方法如下: 1.右键选择数据库,选择“任务”--->“生成脚本” 2.根据需求,选择制作脚本的对象,一般情况选择“表” 3 ...

  4. POJ_2184_Cow_Exhibition_(动态规划,背包)

    描述 http://poj.org/problem?id=2184 n只奶牛,每只都有智商s_i和情商f_i,取出若干只,保证智商之和与情商之和都不为负的情况下,让两者之和最大. Cow Exhibi ...

  5. JavaScript几种类工厂实现原理剖析

    PS:本文参考了司徒正美的<JavaScript框架设计>,以及许多其它的书籍和网络文章,感谢作者们分享了这么好的学习资源!关于JS的类和继承的原理,见:JavaScript里的类和继承文 ...

  6. 解决Subclipse1.6在64位JDK下不可用的问题

    Failed to load JavaHL Library.  These are the errors that were encountered:   需要下载SVNKit Adapter Sub ...

  7. Android环境rm命令

    How can I execute all the possible unix(shell) commands in android programmatically? Android can't e ...

  8. HDOJ/HDU 2565 放大的X(分段思考~)

    Problem Description 请你编程画一个放大的'X'. 如3*3的'X'应如下所示: X X XX X5*5的'X'如下所示:X X X X X X XX X Input 输入数据第一行 ...

  9. Android图形系统之Surface、SurfaceView、SurfaceHolder及SurfaceHolder.Callback开发实例

    原文:Android图形系统之Surface.SurfaceView.SurfaceHolder及SurfaceHolder.Callback之间的联系 Surface是原始图像缓冲区(raw buf ...

  10. weekend110(Hadoop)的 第五天笔记

    (2015年1月24日) 课程目录 01-zookeeper1 02-zookeeper2 03-NN高可用方案的要点1 04-hadoop-HA机制的配置文件 05-hadoop分布式集群HA模式部 ...