天天看點

prototype屬性的作用

為了解決構造函數的對象執行個體之間無法共享屬性的缺點,js提供了prototype屬性。

  js中每個資料類型都是對象(除了null和undefined),而每個對象都繼承自另外一個對象,後者稱為“原型”(prototype)對象,隻有null除外,它沒有自己的原型對象。

  原型對象上的所有屬性和方法,都會被對象執行個體所共享。

  通過構造函數生成對象執行個體時,會将對象執行個體的原型指向構造函數的prototype屬性。每一個構造函數都有一個prototype屬性,這個屬性就是對象執行個體的原型對象。

function 
         Person(name,height){
        

         this
         .name=name;
        

         this
         .height=height;
        

         } 
        

         Person.prototype.hobby=
         function
         (){
        

         return 
         'watching movies'
         ;
        

         }
        

         var 
         boy=
         new 
         Person(
         'keith'
         ,180);
        

         var 
         girl=
         new 
         Person(
         'rascal'
         ,153); 
        

         console.log(boy.name); 
         //'keith'
        

         console.log(girl.name); 
         //'rascal'
        

         console.log(boy.hobby===girl.hobby); 
         //true      

  上面代碼中,如果将hobby方法放在原型對象上,那麼兩個執行個體對象都共享着同一個方法。我希望大家都能了解的是,對于構造函數來說,prototype是作為構造函數的屬性;對于對象執行個體來說,prototype是對象執行個體的原型對象。是以prototype即是屬性,又是對象。

  原型對象的屬性不是對象執行個體的屬性。對象執行個體的屬性是繼承自構造函數定義的屬性,因為構造函數内部有一個this關鍵字來指向将要生成的對象執行個體。對象執行個體的屬性,其實就是構造函數内部定義的屬性。隻要修改原型對象上的屬性和方法,變動就會立刻展現在所有對象執行個體上。

Person.prototype.hobby=
         function
         (){
        

          
         return 
         'swimming'
         ;
        

          
         }
        

          
         console.log(boy.hobby===girl.hobby); 
         //true
        

          
         console.log(boy.hobby()); 
         //'swimming'
        

         console.log(girl.hobby()); 
         //'swimming'      

  上面代碼中,當修改了原型對象的hobby方法之後,兩個對象執行個體都發生了變化。這是因為對象執行個體其實是沒有hobby方法,都是讀取原型對象的hobby方法。也就是說,當某個對象執行個體沒有該屬性和方法時,就會到原型對象上去查找。如果執行個體對象自身有某個屬性或方法,就不會去原型對象上查找。

boy.hobby=
         function
         (){
        

          
         return 
         'play basketball'
         ;
        

          
         }
        

          
         console.log(boy.hobby()); 
         //'play basketball'
        

          
         console.log(girl.hobby()); 
         //'swimming'      

  上面代碼中,boy對象執行個體的hobby方法修改時,就不會在繼承原型對象上的hobby方法了。不過girl仍然會繼承原型對象的方法。

繼續閱讀