我所理解的JavaScript中的prototype与__proto__、constructor

前几天当我同时向往说起node.js的时候,我逐渐发现原来JS是个多么丰富语言——我原来一直都在井底(初学者的悲哀)。当我想认认真真学习JavaScript的时候,我发现prototype与__proto__、constructor这几个家伙老是让我很有挫败感(学一门语言属性都搞不懂,还学个P)。但我是一个不轻易服输的人,也不是不会妥协,就是有这种习惯,我就要去做就要去弄懂哪怕挫折感更多。于是,我在网上搜大神们的对这几个让我烦恼的东西的阐述与解释。最后的结果是--还是搞不懂。“什么对象原型,什么内部原型”,难道是孙悟空吗?这么多变身。后来在看“javascript语言精髓与编程实践精简版”的时候突然让我了解了__proto__与prototype的真实面目。

这里我借鉴一张图([url]http://anykoro.sinaapp.com/2012/01/31/javascript%E4%B8%ADfunctionobjectprototypes__proto__等概念详解[/url])其他的文章如果想真正了解的就不要看了,越看越迷糊(有些人不懂或者说半懂就给上面的三个家伙乱下定义,搞的我云里雾里,误人子弟)。我在这里只用比喻,也就说我说的prototype与__proto__与constructor是我所理解的模型,而不是给他死下定义,每个人的理解是可以不同的知识不要搞的那么专业化,像是你能给他下定义似得(装大神,误人子弟)。

function能够调用的prototype一般被定义为“对象原型的引用”,有的人也说是"实例"(一开始我以Java的理念理解,真是把我搞醉了)。我对于prototype的理解就是“爸爸”,也就是对象的模子。当我们对prototype添加属性的时候"模子"会改变它的形状,以后用这个模子造出来的实例(var x = new X;)就会是按照模子来做的,所以说他的实例就会拥有prototype的属性。如果我们用"X.prototype="的形式就会改变它的模子也就是换一个“爸爸”,所以这样做不会是一点点改变了,而是替换(就是找继父)。所以说在执行这句话的时候,就会改变X的生出来的孩子的属性。如果还是不懂就弄清我给你们的链接加上自己做实验。

__proto__在我的理解里是“影子”或者说父类的属性视图。用 "var X =  function (){}或者function X() {}  var x = new X();"的时候x中的__proto__属性会指向X.prototype.这是原型链中最恒等的,不管prototype改变还是__proto__改变,这条链始终是要相等。

<code>

//原文的例子,有些许错误。在他的例子上有些许改进。

function Foo(){

}

Foo.__proto__.test="__proto__ test property found";//通过__proto__扩展Foo.__proto__.addextend=function(){alert("Foo add extend by __proto__");}
alert(Function.prototype.test);//可以访问,这里为什么对象的是Function.prototype呢?相信Foo.__proto__是儿子,而爸爸是谁呢?Function.prototype
var foo=new Foo;
foo.__proto__.lab = "abc";
alert(foo.__proto__===Foo.prototype);

</code>

上面这段代码对Foo的__proto__进行添加(其实对Foo.__proto__的改变按道理说是对应Function.prototype.test,foo的__proto__是对应Foo的prototype,这条关系永远的恒等的),而__proto__是特殊的影子或者视图(就像Oracle数据库),你修改它是会影响到Function的prototype的,如果你在上面代码后面添加

<code>

for(var x in foo.__proto__){    alert(x);}for(var y in Foo.prototype){    alert(Foo.prototype.lab);}
alert(foo.lab);

</code>

是可以访问到lab(中文翻译:实验)这个属性的。所以说,就这一单来说__proto__类似于数据库中的视图,这是很奇特的就像儿子反过来会影响爸爸(多好的一家人)。

而理解constructor的时候可以把prototype看做是一个实例,就如Foo的prototype(实例)的构造函数不就是指向函数本身吗!也就是说Foo.prototype.constructor的与foo.constructor的是一样的。而Foo.constructor是Function(这里可以解释为构造Foo的构造函数不就是new Function())这里其实对于prototype的理解我也不能很好的去统一,大家只能自己意会了(分开理解会更加清楚)。

总之,我认为(以我学习几天的JavaScript的立场)来说,Foo.prototype就是就是其new 出来的实例的__proto__的 "爸爸"或者说"真身",而foo.__proto__的则是类的“影子”或者是“视图”(特殊的),当爸爸改变的时候生出来的儿子当然不同,但是儿子改变是爸爸也会变化(只能自己理解,我真说不清楚了)。而constructor就是构造对象的属性了,注意是对象(JavaScript中一切皆对象,所以function本身也是对象,也会有constructor的,所有产生function的都是大Function(通过 new Function();的方式可以看到)).小foo的构造当然是 大Foo,大Foo的实例(prototype)的构造函数当然也是大Foo.所以才会有Foo的prototype的constructor指向他本身的说法。完毕!(PS:虽然是刚刚学习JavaScript,但我认为这样理解这三个东西,是我唯一能够接受的理解方式了,有不同的理解又不产生歧义的可以用自己理解的方式。如果,你看完任然感觉迷惑,就按照你自己的来吧)

时间: 2024-08-04 14:32:29

我所理解的JavaScript中的prototype与__proto__、constructor的相关文章

JavaScript中的prototype和__proto__细致解析

最近在学js,体会了一点点它的灵活性.对于初学者的我,总是被它的灵活感到晕头转向,最近发现了一点东西想与大家分享. JavaScript中的prototype和_proto_: 我们先了解一点js中的基础知识,首先我们先看一段js代码: 1 var object = new Object; 2 console.log("object:", object); 3 object.member1 = "abcd"; 4 5 var obj = {}; 6 obj.memb

JavaScript 中 的prototype和__proto__

1.prototype是函数的一个属性(每个函数都有一个prototype属性),这个属性是一个指针,指向一个对象.它是显示修改对象的原型的属性. 2.__proto__是一个对象拥有的内置属性(请注意:prototype是函数的内置属性,__proto__是对象的内置属性),是JS内部使用寻找原型链的属性.

JS/javascript中的prototype和__proto__

// 创建一个Dog构造函数 function Dog(name, age) { // ① this.name = name this.age = age } Dog.prototype.eat = function() { // ② console.log('肉骨头真好吃') } // 使用Dog构造函数创建dog实例 const dog = new Dog('旺财', 3) 图by 修言 dog.__proto__和Dog.prototype 均指向function Dog,也就是① 原文地

理解javascript中的prototype

以前一直对javascript中的prototype不是很理解,今天在阅读了<javascript高级程序设计之后>终于理解了其中的prototype.来简单的总结一下从书中学习到的内容. 我们都知道在创建了一个function之后,这个function就具有了prototype这样的一个属性,利用这个prototype我们可以做很多的事情,其中我们经常用到的一点就是利用它来当做构造函数,因此,本文重要从function作为构造函数的角度来说明一下prototype. 其实javascript

JavaScript中Object.prototype.toString方法的原理

在JavaScript中,想要判断某个对象值属于哪种内置类型,最靠谱的做法就是通过Object.prototype.toString方法. ? 1 2 var arr = []; console.log(Object.prototype.toString.call(arr)) //"[object Array]" 本文要讲的就是,toString方法是如何做到这一点的,原理是什么. ECMAScript 3 在ES3中,Object.prototype.toString方法的规范如下:

原型链继承中的prototype、__proto__和constructor的关系

前不久写了有关原型链中prototype.__proto__和constructor的关系的理解,这篇文章说说在原型链继承中的prototype.__proto__和constructor的关系. 通过以下最简单的原型链继承(省略了属性和方法)来讨论: 1 function SuperType(){}; 2 function SubType(){}; //继承了SuperType 3 SubType.protoType = new SuperType(); //创建了一个SubType的实例 4

深入理解Javascript中this, prototype, constructor

在Javascript面向对象编程中经常需要使用到this,prototype和constructor这3个关键字. 1.首先介绍一下this的使用:this表示当前对象;如果在全局中使用this,则this为当前页面对象window;如果在函数中使用this,则this为调用该函数的对象;可以使用apply和call两个全局函数来改变this的指向. 接下来,首先通过几个demo程序验证一下: function testFunction(){ console.log(this.variable

JavaScript——中的prototype(原型)

JS中的prototype是JS中比较难理解的一个部分 本文基于下面几个知识点: 1 原型法设计模式 在.Net中可以使用clone()来实现原型法 原型法的主要思想是,现在有1个类A,我想要创建一个类B,这个类是以A为原型的,并且能进行扩展.我们称B的原型为A. 2 javascript的方法可以分为三类: a 类方法 b 对象方法 c 原型方法 例子: function People(name){  this.name=name;  //对象方法  this.Introduce=functi

javascript中的prototype详细解释

本文基于下面几个知识点: 1.在.Net中可以使用clone()来实现原型法原型法的主要思想是,现在有1个类A,我想要创建一个类B,这个类是以A为原型的,并且能进行扩展.我们称B的原型为A. 2.javascript的方法可以分为三类: a 类方法 b 对象方法 c 原型方法 例子: function People(name) { this.name=name; //对象方法 this.Introduce=function(){ alert("My name is "+this.nam