JS prototype

作为互联网 的 当今,js 越来越成为 不可或缺的一种 脚本语言。那么 js 中最重要的 概念,原型到底是个啥,读了下面文章,会有个初认识:

本文翻译至:http://www.mollypages.org/misc/js.mp

                                  技术分享

初看这图,也是看不懂呀。那咱先翻译出来吧

 

    1. 所有的实例都继承至创建他们函数的原型;
         也就是说var f =new foo();   f 继承至foo.prototype  

     2 . Mozilla/Konqueror 有特殊的 属性 __proto__ ,这个属性指向创建实例函数的原型;

      

  var f= new foo(); f.__proto__ === foo.prototype;结果是 true; 在chrom ,火狐浏览器都存在__proto__属性;

   

  3.不管存在不存在 __proto__ 属性,我们都建议 对象 使用 prototype 对象 指向创建该对象的函数,这个prototype 是javascript标准的一部分,被称作为 “原型”。默认情况下,prototype 存在一个constructor 属性 指回到 创建实例的函数;

  

  4.prototype只能被用作 实例/对象 的属性继承,和创建这些 实例/对象的 函数无关(but 这个函数本身也是 对象的话,他继承至 创建他的 函数的原型对象,经典的就是 javascript 系统 的“Function”对象 ) 

   

functionFoo() { } ;

var f1 = new Foo();

 

Foo.prototype.x= "hello";

f1.x   //=> hello

Foo.x//=> undefined

  

  5.默认的prototype 对象可以 被用户创建的对象替换. 当这么做时,constructor属性必须得手动的复制,确保js 运行时在默认的原型对象的场景下 ;

functionfoo() { } ; var f1 = new foo();

f1.constructor === foo.prototype.constructor === foo 

//replacethe default prototype object

foo.prototype= new Object();

//createanother instance l

f1 = new foo();

//now wehave:

f1.constructor === foo.prototype.constructor === Object

//so now wesay:

foo.prototype.constructor= foo

//all iswell again

f1.constructor === foo.prototype.constructor === foo

 

    6.所有原型对象本身(默认)创建至 Object() 构造函数,因此,prototype 存在 原型对象的原型是 Object.prototype 。所以,

       所有 对象/实例,不管是什么类型的,其属性都最终继承至Object.prototype ; 

     

functionFoo(){}

var f = newFoo();

 

//Foo.prototype= new Object();

//so

//Foo.prototype.prototype= Object.prototype ;

 

//f 继承至 Foo.prototype ; Foo.protype 继承至 Object.prototype ;最终 f 继承于 Object.prototype

 

Object.prototype.Name= "WSP"; = "WSP";

console.log(f.Name);//WSP

    

  7.所有的对象自动的 从 原型链 里读取属性,就好像,这些属性定义在 这些对象自己本身一样 

        7.1 通过设置相同的 属性来隐藏该对象 原型中相同的属性;看如下代码 

functionfoo() { }

f1 = new foo();

f2 = new foo();

foo.prototype.x= "hello";

 

f1.x  =>"hello"

f2.x  => "hello";

 

f1.x = "goodbye";   //setting f1.x hidesfoo.prototype.x

 

f1.x  =>"goodbye"  //hides"hello" for f1 only

f2.x  => "hello"

 

delete f1.x

f1.x  =>"hello";   //foo.prototype.x isvisible again to f1.

      7.2 直接在 prototype 中设置 属性来 影响 所有实例 

foo.prototype.x= "goodbye";

//now

f1.x  =>"goodbye"

f2.x  => "goodbye";

     

扩展点:

     以下是一些javascript 有趣的关系, 你感兴趣的话,可以把这些代码敲到你  的 js控制台来玩玩。

     

     1.Function.__ptoto__ 指向 Function.prototype ,由此会产生:

       Function.constructor === Function ; 

       也就是说 Function 是他自己的构造函数   

     2.Object instanceof Obect=== true;
        这是因为 Object.__proto__.__proto__.constructor ==Object;
        

       但是 不同于 Foo instanceof Foo === false; 

       Foo.__proto__.__proto__.constructor=== Object; 
       Foo 在他自己的原型链中没有 作为 构造函数;

       3. Function.prototype.toString 是内置函数但不同于 另外一个内置函数:Object.prototype.toString ;

                            

function Foo(){};

var f1 = new Foo();

 

//ok 现在我们 设置内置函数toString();

Object.prototype.toString= function (){ console.log("I amObject.toString");};

Function.prototype.toString = function(){ console.log("I am Function.toString"); };

 

f1.toString(); // 输出啥,你们可以自己试试哦

Foo.toString();//

 

delete Function.prototype.toString;

Foo.toString()//现在又是输出啥?留给你自己敲着试试


Note: (分析的伪代码 ) f1.toString  寻找 路径是这样 的  首先会寻找 f1-->Foo.prototype --> Foo.prototype.prototype (Object.prototype) 刚好存在toString 方法 Ok 执行

      Foo.toString ---------------Foo 是函数, Foo.prototype 指向的是创建 Foo对象的prototype ,也就是 Function.prototype

                                   Foo---->Function.prototype 存在toString方法,Ok执行 

 

delete Function.prototype.toString;

 

 foo--->Function.prototype---> function.prototype.prototype ( 也就是 Object.prototype) 存在 toString 函数OK,执行

 

 

郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。