JavaScript中要實(shí)現繼承,其實(shí)就是實(shí)現三層含義:1、子類(lèi)的實(shí)例可以共享父類(lèi)的方法;2、子類(lèi)可以覆蓋父類(lèi)的方法或者擴展新的方法;3、子類(lèi)和父類(lèi)都是子類(lèi)實(shí)例的“類(lèi)型”。
JavaScript中,并不直接從語(yǔ)法上支持繼承,但是可以通過(guò)模擬的方法來(lái)實(shí)現繼承,以下是關(guān)于實(shí)現繼承的幾種方法的總結:1、構造繼承法2、原型繼承法3、實(shí)例繼承法4、拷貝繼承法1、構造繼承法:在子類(lèi)中執行父類(lèi)的構造函數。 12、原型繼承法:JavaScript是一種基于原型的語(yǔ)言。
要了解什么是“原型繼承法”,先了解一下prototype的特性:prototype的最大特性是能夠讓對象實(shí)例共享原型對象的屬性,因此如果把某個(gè)對象作為一個(gè)類(lèi)型的原型,那么我們說(shuō)這個(gè)類(lèi)型的所有實(shí)例都一這個(gè)對象為原型。這個(gè)時(shí)候,實(shí)際上這個(gè)對象的類(lèi)型也可以作為那些以這個(gè)對象為原型的實(shí)例的類(lèi)型。
假如:Point類(lèi)的對象作為Point2D類(lèi)型的原型(Point2D.prototype = new Point(2)),那么說(shuō)Point2D的所有實(shí)例都是以Point類(lèi)的對象為原型。此時(shí),實(shí)際上Point類(lèi)就可以作為Point2D類(lèi)型的對象的類(lèi)型(相當于Point2D類(lèi)型“繼承”了Point類(lèi)型)。
見(jiàn)例:1 <script LANGUAGE="JavaScript"> 2 方法,可以被繼承14 {15 return this.dimension*2;16 }1718 function Point2D(x,y) //定義一個(gè)Point2D類(lèi)19 {20 this.x = x;21 this.y = y;22 }2324 Point2D.prototype = new Point(2); //運行“原型繼承法”使Point2D繼承Point2526 function Point3D(x,y,z) //定義Point3D類(lèi)27 {28 this.x = x;29 this.y = y;30 this.z = z;31 }3233 Point3D.prototype = new Point(3); //Point3D繼承Point類(lèi)3435 var p2 = new Point2D(1,2); //構造一個(gè)Point2D對象3637 var p3 = new Point3D(1,2,3); //構造一個(gè)Point3D對象3839 dwn(p2.dimension); //240 dwn(p3.dimension); //341 dwn(p2.distance()); //4 可以繼承靜態(tài)方法42 dwn(p3.distance()); //6 可以繼承靜態(tài)方法<。
js繼承用的還是比較少的,一般通過(guò)原型鏈繼承或混合繼承目的就是降低創(chuàng )建對象的開(kāi)銷(xiāo)!各種繼承示例如下:構造函數繼承:原型鏈繼承:混合繼承:ES6 extends繼承:。
Js的繼承方式有以下方式:// 定義一個(gè)動(dòng)物類(lèi)為父類(lèi)function Animal (name) { // 屬性 this.name = name || 'Animal'; // 實(shí)例方法 this.sleep = function(){ console.log(this.name + '正在睡覺(jué)!'); }}// 原型方法Animal.prototype.eat = function(food) { console.log(this.name + '正在吃:' + food);};1、原型鏈繼承核心: 將父類(lèi)的實(shí)例作為子類(lèi)的原型function Cat(){ }Cat.prototype = new Animal();Cat.prototype.name = 'cat';// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.eat('fish'));console.log(cat.sleep());console.log(cat instanceof Animal); //true console.log(cat instanceof Cat); //true特點(diǎn):1. 非常純粹的繼承關(guān)系,實(shí)例是子類(lèi)的實(shí)例,也是父類(lèi)的實(shí)例2. 父類(lèi)新增原型方法/原型屬性,子類(lèi)都能訪(fǎng)問(wèn)到3. 簡(jiǎn)單,易于實(shí)現缺點(diǎn):1. 在Cat構造函數中,為Cat實(shí)例增加實(shí)例屬性。
如果要新增原型屬性和方法,則必須放在new Animal()這樣的語(yǔ)句之后執行。2. 無(wú)法實(shí)現多繼承3. 來(lái)自原型對象的引用屬性是所有實(shí)例共享的(詳細請看附錄代碼: 示例1)4. 創(chuàng )建子類(lèi)實(shí)例時(shí),無(wú)法向父類(lèi)構造函數傳參推薦指數:★★(3、4兩大致命缺陷)2、構造繼承核心:使用父類(lèi)的構造函數來(lái)增強子類(lèi)實(shí)例,等于是復制父類(lèi)的實(shí)例屬性給子類(lèi)(沒(méi)用到原型)function Cat(name){ Animal.call(this); this.name = name || 'Tom';}// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // falseconsole.log(cat instanceof Cat); // true特點(diǎn):1. 解決了1中,子類(lèi)實(shí)例共享父類(lèi)引用屬性的問(wèn)題2. 創(chuàng )建子類(lèi)實(shí)例時(shí),可以向父類(lèi)傳遞參數3. 可以實(shí)現多繼承(call多個(gè)父類(lèi)對象)缺點(diǎn):1. 實(shí)例并不是父類(lèi)的實(shí)例,只是子類(lèi)的實(shí)例2. 只能繼承父類(lèi)的實(shí)例屬性和方法,不能繼承原型屬性/方法3. 無(wú)法實(shí)現函數復用,每個(gè)子類(lèi)都有父類(lèi)實(shí)例函數的副本,影響性能推薦指數:★★(缺點(diǎn)3)3、實(shí)例繼承核心:為父類(lèi)實(shí)例添加新特性,作為子類(lèi)實(shí)例返回function Cat(name){ var instance = new Animal(); instance.name = name || 'Tom'; return instance;}// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // trueconsole.log(cat instanceof Cat); // false特點(diǎn):1. 不限制調用方式,不管是new 子類(lèi)()還是子類(lèi)(),返回的對象具有相同的效果缺點(diǎn):1. 實(shí)例是父類(lèi)的實(shí)例,不是子類(lèi)的實(shí)例2. 不支持多繼承推薦指數:★★4、拷貝繼承function Cat(name){ var animal = new Animal(); for(var p in animal){ Cat.prototype[p] = animal[p]; } Cat.prototype.name = name || 'Tom';}// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // falseconsole.log(cat instanceof Cat); // true特點(diǎn):1. 支持多繼承缺點(diǎn):1. 效率較低,內存占用高(因為要拷貝父類(lèi)的屬性)2. 無(wú)法獲取父類(lèi)不可枚舉的方法(不可枚舉方法,不能使用for in 訪(fǎng)問(wèn)到)推薦指數:★(缺點(diǎn)1)5、組合繼承核心:通過(guò)調用父類(lèi)構造,繼承父類(lèi)的屬性并保留傳參的優(yōu)點(diǎn),然后通過(guò)將父類(lèi)實(shí)例作為子類(lèi)原型,實(shí)現函數復用function Cat(name){ Animal.call(this); this.name = name || 'Tom';}Cat.prototype = new Animal();// 組合繼承也是需要修復構造函數指向的。
Cat.prototype.constructor = Cat;// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // trueconsole.log(cat instanceof Cat); // true特點(diǎn):1. 彌補了方式2的缺陷,可以繼承實(shí)例屬性/方法,也可以繼承原型屬性/方法2. 既是子類(lèi)的實(shí)例,也是父類(lèi)的實(shí)例3. 不存在引用屬性共享問(wèn)題4. 可傳參5. 函數可復用缺點(diǎn):1. 調用了兩次父類(lèi)構造函數,生成了兩份實(shí)例(子類(lèi)實(shí)例將子類(lèi)原型上的那份屏蔽了)推薦指數:★★★★(僅僅多消耗了一點(diǎn)內存)6、寄生組合繼承核心:通過(guò)寄生方式,砍掉父類(lèi)的實(shí)例屬性,這樣,在調用兩次父類(lèi)的構造的時(shí)候,就不會(huì )初始化兩次實(shí)例方法/屬性,避免的組合繼承的缺點(diǎn)function Cat(name){ Animal.call(this); this.name = name || 'Tom';}(function(){ // 創(chuàng )建一個(gè)沒(méi)有實(shí)例方法的類(lèi) var Super = function(){}; Super.prototype = Animal.prototype; //將實(shí)例作為子類(lèi)的原型 Cat.prototype = new Super();})();// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // trueconsole.log(cat instanceof Cat); //true//該實(shí)現沒(méi)有修復constructor。Cat.prototype.constructor = Cat; // 需要修復下構造函數特點(diǎn):1. 堪稱(chēng)完美缺點(diǎn):1. 實(shí)現較為復雜推薦指數:★★★★(實(shí)現復雜,扣掉一顆星)示例代碼:function Animal (name) { // 屬性 this.name = name || 'Animal'; // 實(shí)例方法 this.sleep = function(){ console.log(this.name + '正在睡覺(jué)!'); } //實(shí)例引用屬性 this.features = [];}function Cat(name){}Cat.prototype = new Animal();var tom = new Cat('Tom');var kissy = new Cat('Kissy');console.log(tom.name); // "Animal"console.log(kissy.name); // "Animal"console.log(tom.features); // []console.log(kissy.features); 。
Js的繼承方式有以下方式: // 定義一個(gè)動(dòng)物類(lèi)為父類(lèi)function Animal (name) { // 屬性 this.name = name || 'Animal'; // 實(shí)例方法 this.sleep = function(){ console.log(this.name + '正在睡覺(jué)!'); }}// 原型方法Animal.prototype.eat = function(food) { console.log(this.name + '正在吃:' + food);};1、原型鏈繼承核心: 將父類(lèi)的實(shí)例作為子類(lèi)的原型 function Cat(){ }Cat.prototype = new Animal();Cat.prototype.name = 'cat';// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.eat('fish'));console.log(cat.sleep());console.log(cat instanceof Animal); //true console.log(cat instanceof Cat); //true特點(diǎn): 非常純粹的繼承關(guān)系,實(shí)例是子類(lèi)的實(shí)例,也是父類(lèi)的實(shí)例父類(lèi)新增原型方法/原型屬性,子類(lèi)都能訪(fǎng)問(wèn)到簡(jiǎn)單,易于實(shí)現缺點(diǎn): 在Cat構造函數中,為Cat實(shí)例增加實(shí)例屬性。
如果要新增原型屬性和方法,則必須放在new Animal()這樣的語(yǔ)句之后執行。無(wú)法實(shí)現多繼承來(lái)自原型對象的引用屬性是所有實(shí)例共享的(詳細請看附錄代碼: 示例1)創(chuàng )建子類(lèi)實(shí)例時(shí),無(wú)法向父類(lèi)構造函數傳參推薦指數:★★(3、4兩大致命缺陷)2、構造繼承核心:使用父類(lèi)的構造函數來(lái)增強子類(lèi)實(shí)例,等于是復制父類(lèi)的實(shí)例屬性給子類(lèi)(沒(méi)用到原型) function Cat(name){ Animal.call(this); this.name = name || 'Tom';}// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // falseconsole.log(cat instanceof Cat); // true特點(diǎn): 解決了1中,子類(lèi)實(shí)例共享父類(lèi)引用屬性的問(wèn)題創(chuàng )建子類(lèi)實(shí)例時(shí),可以向父類(lèi)傳遞參數可以實(shí)現多繼承(call多個(gè)父類(lèi)對象) 缺點(diǎn): 實(shí)例并不是父類(lèi)的實(shí)例,只是子類(lèi)的實(shí)例只能繼承父類(lèi)的實(shí)例屬性和方法,不能繼承原型屬性/方法無(wú)法實(shí)現函數復用,每個(gè)子類(lèi)都有父類(lèi)實(shí)例函數的副本,影響性能 推薦指數:★★(缺點(diǎn)3)3、實(shí)例繼承核心:為父類(lèi)實(shí)例添加新特性,作為子類(lèi)實(shí)例返回 function Cat(name){ var instance = new Animal(); instance.name = name || 'Tom'; return instance;}// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // trueconsole.log(cat instanceof Cat); // false特點(diǎn): 不限制調用方式,不管是new 子類(lèi)()還是子類(lèi)(),返回的對象具有相同的效果缺點(diǎn): 實(shí)例是父類(lèi)的實(shí)例,不是子類(lèi)的實(shí)例不支持多繼承推薦指數:★★4、拷貝繼承function Cat(name){ var animal = new Animal(); for(var p in animal){ Cat.prototype[p] = animal[p]; } Cat.prototype.name = name || 'Tom';}// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // falseconsole.log(cat instanceof Cat); // true特點(diǎn): 支持多繼承缺點(diǎn): 效率較低,內存占用高(因為要拷貝父類(lèi)的屬性)無(wú)法獲取父類(lèi)不可枚舉的方法(不可枚舉方法,不能使用for in 訪(fǎng)問(wèn)到)推薦指數:★(缺點(diǎn)1)5、組合繼承核心:通過(guò)調用父類(lèi)構造,繼承父類(lèi)的屬性并保留傳參的優(yōu)點(diǎn),然后通過(guò)將父類(lèi)實(shí)例作為子類(lèi)原型,實(shí)現函數復用 function Cat(name){ Animal.call(this); this.name = name || 'Tom';}Cat.prototype = new Animal();// 組合繼承也是需要修復構造函數指向的。
Cat.prototype.constructor = Cat;// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // trueconsole.log(cat instanceof Cat); // true特點(diǎn): 彌補了方式2的缺陷,可以繼承實(shí)例屬性/方法,也可以繼承原型屬性/方法既是子類(lèi)的實(shí)例,也是父類(lèi)的實(shí)例不存在引用屬性共享問(wèn)題可傳參函數可復用缺點(diǎn): 調用了兩次父類(lèi)構造函數,生成了兩份實(shí)例(子類(lèi)實(shí)例將子類(lèi)原型上的那份屏蔽了)推薦指數:★★★★(僅僅多消耗了一點(diǎn)內存)6、寄生組合繼承核心:通過(guò)寄生方式,砍掉父類(lèi)的實(shí)例屬性,這樣,在調用兩次父類(lèi)的構造的時(shí)候,就不會(huì )初始化兩次實(shí)例方法/屬性,避免的組合繼承的缺點(diǎn) function Cat(name){ Animal.call(this); this.name = name || 'Tom';}(function(){ // 創(chuàng )建一個(gè)沒(méi)有實(shí)例方法的類(lèi) var Super = function(){}; Super.prototype = Animal.prototype; //將實(shí)例作為子類(lèi)的原型 Cat.prototype = new Super();})();// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // trueconsole.log(cat instanceof Cat); //true//該實(shí)現沒(méi)有修復constructor。Cat.prototype.constructor = Cat; // 需要修復下構造函數特點(diǎn): 堪稱(chēng)完美缺點(diǎn): 實(shí)現較為復雜推薦指數:★★★★(實(shí)現復雜,扣掉一顆星)示例代碼: function Animal (name) { // 屬性 this.name = name || 'Animal'; // 實(shí)例方法 this.sleep = function(){ console.log(this.name + '正在睡覺(jué)!'); } //實(shí)例引用屬性 this.features = [];}function Cat(name){}Cat.prototype = new Animal();var tom = new Cat('Tom');var kissy = new Cat('Kissy');console.log(tom.name); // "Animal"console.log(kissy.name); // "Animal"console.log(tom.features); // []console.log(kissy.features); // []tom.name = 'Tom-New Name';tom.features.push('eat'。
繼承的方式一共有三種:一、原型繼承通過(guò)prototype 來(lái)實(shí)現繼承。
function Person(name,age) { this.name=name; this.age=age;}Person.prototype.sayHello=function(){alert (''使用原型得到Name:'' + this.name);} var per = new Person(";馬小倩",21);per.sayHello();//輸出:使用原型得到Name:馬小倩 function Student(){}Student.prototype=new Person(";洪如彤",21); //實(shí)現原型繼承var stu = new Student();Student.prototype.grade=5; Student.prototype.intr=function(){alert(this.grade);} stu.sayHello();//輸出:使用原型得到Name:洪如彤stu.intr();//輸出:5 二、構造函數實(shí)現繼承function Person(name,age) { this.name=name; this.age=age;}Person.prototype.sayHello=function(){alert (''使用原型得到Name:'' + this.name);} var per = new Person(";馬小倩",21);per.sayHello();//輸出:使用原型得到Name:馬小倩三、通過(guò)call、apply 實(shí)現繼承。
定義一個(gè)父類(lèi):// 定義一個(gè)動(dòng)物類(lèi)function Animal (name) {// 屬性this.name = name || 'Animal';// 實(shí)例方法this.sleep = function(){console.log(this.name + '正在睡覺(jué)!');}}// 原型方法Animal.prototype.eat = function(food) {console.log(this.name + '正在吃:' + food);1.原型鏈繼承核心:將父類(lèi)的實(shí)例作為子類(lèi)的原型function Cat(){}Cat.prototype = new Animal();Cat.prototype.name = 'cat';// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.eat('fish'));console.log(cat.sleep());console.log(cat instanceof Animal); //trueconsole.log(cat instanceof Cat); //true特點(diǎn):1.非常純粹的繼承關(guān)系,實(shí)例是子類(lèi)的實(shí)例,也是父類(lèi)的實(shí)例 2.父類(lèi)新增的原型方法、屬性,子類(lèi)都能訪(fǎng)問(wèn)到 3.簡(jiǎn)單,易于實(shí)現缺點(diǎn):1.要想為子類(lèi)新增屬性和方法,必須要在new Animal()這樣的語(yǔ)句之后執行(可以在cat構造函數中,為Cat實(shí)例增加實(shí)例屬性)2.無(wú)法實(shí)現多繼承3.來(lái)自原型對象的引用屬性被所有實(shí)例共享 4.創(chuàng )建子類(lèi)實(shí)例時(shí),無(wú)法向父類(lèi)構造函數傳參下面代碼解釋缺點(diǎn)3(注意是引用屬性):function Super(){ this.val = 1; this.arr = [1];}function Sub(){ // 。
}Sub.prototype = new Super(); // 核心var sub1 = new Sub();var sub2 = new Sub();sub1.val = 2;sub1.arr.push(2);alert(sub1.val); // 2alert(sub2.val); // 1alert(sub1.arr); // 1, 2alert(sub2.arr); // 1, 22.構造繼承核心:使用父類(lèi)的構建函數來(lái)增強子類(lèi)實(shí)例,等于復制父類(lèi)的實(shí)例屬性給子類(lèi)(沒(méi)用到原型),除了call方法,也可以用apply()function Cat(name){Animal.call(this);this.name = name || 'Tom';}// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // falseconsole.log(cat instanceof Cat); // true特點(diǎn):1.解決了1中,子類(lèi)實(shí)例共享父類(lèi)引用屬性的問(wèn)題 2.創(chuàng )建子類(lèi)實(shí)例時(shí),可以向父類(lèi)傳遞參數 3.可以實(shí)現多繼承(call多個(gè)父類(lèi)對象)缺點(diǎn):1.實(shí)例并不是父類(lèi)的實(shí)例,只是子類(lèi)的實(shí)例 2.只能繼承父類(lèi)的實(shí)例屬性和方法,不能繼承原型屬性和方法 3.無(wú)法實(shí)現函數復用,每個(gè)子類(lèi)都有父類(lèi)的實(shí)例函數的副本,影響性能3.實(shí)例繼承核心:為父類(lèi)實(shí)例添加新特性,作為子類(lèi)實(shí)例返回function Cat(name){var instance = new Animal();instance.name = name || 'Tom';return instance;}// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // trueconsole.log(cat instanceof Cat); // false特點(diǎn):1.不限制調用方式,不管是new 子類(lèi)()還是子類(lèi)(),返回的對象都具有相同的效果缺點(diǎn):1.實(shí)例是父類(lèi)的實(shí)例,不是子類(lèi)的實(shí)例2.不支持多繼承4. 拷貝繼承核心:使用for…in將父類(lèi)實(shí)例中的方法賦給子類(lèi)實(shí)例unction Cat(name){var animal = new Animal();for(var p in animal){Cat.prototype[p] = animal[p];}Cat.prototype.name = name || 'Tom';}// Test Codevar cat = new Cat();console.log(cat.name);console.log(cat.sleep());console.log(cat instanceof Animal); // falseconsole.log(cat instanceof Cat); // true特點(diǎn):1.支持多繼承缺點(diǎn):1.效率較低,內存占用高(因為要拷貝父類(lèi)的屬性)2.無(wú)法獲取父類(lèi)不可枚舉的方法(for in無(wú)法訪(fǎng)問(wèn)不可枚舉的方法)5.組合繼承核心:通過(guò)調用父類(lèi)構造,繼承父類(lèi)的屬性并保留傳參的優(yōu)點(diǎn),然后通過(guò)將父類(lèi)實(shí)例作為子類(lèi)原型,實(shí)現函數復用function Cat(name){Animal.call(this);this.name = name || 'Tom';}Cat.prototype = new Animal();//組合繼承需要修復構造函數的指向Cat.prototype.constructor=Cat;// Test Code var cat = new Cat(); console.log(cat.name); console.log(cat.sleep()); console.log(cat instanceof Animal); // true console.log(cat instanceof Cat); // true特點(diǎn):1.彌補了方式2的缺陷,可以繼承實(shí)例屬性、方法,也可以繼承原型屬性、方法2.既是子類(lèi)的實(shí)例,也是父類(lèi)的實(shí)例3.不存在引用屬性的共享問(wèn)題4.可傳參5.函數可復用缺點(diǎn):1.調用了兩次父類(lèi)構造函數,生成了兩份實(shí)例(子類(lèi)實(shí)例將子類(lèi)原型上的那份屏蔽了)6.寄生組合繼承核心:通過(guò)寄生方式,砍掉父類(lèi)的實(shí)例屬性,這樣,在調用兩次父類(lèi)的構造的時(shí)候,就不會(huì )初始化兩次實(shí)例方法/屬性,避免的組合繼承的缺點(diǎn)function Cat(name){Animal.call(this);this.name = name || 'Tom';}(function(){// 創(chuàng )建一個(gè)沒(méi)有實(shí)例方法的類(lèi)var Super = function(){};Super.prototype = Animal.prototype;//將實(shí)例作為子類(lèi)的原型Cat.prototype = new Super();//寄生組合繼承需要修復構造函數的指向Cat.prototype.constructor=Cat;})(); // Test Code var cat = new Cat(); console.log(cat.name); console.log(cat.sleep()); console.log(cat instanceof Animal); // true console.log(cat instanceof Cat); //true特點(diǎn):1.堪稱(chēng)完美缺點(diǎn):1.實(shí)現較為復雜 (BY三人行慕課)。
1、原型鏈繼承核心: 將父類(lèi)的實(shí)例作為子類(lèi)的原型缺點(diǎn): 父類(lèi)新增原型方法/原型屬性,子類(lèi)都能訪(fǎng)問(wèn)到,父類(lèi)一變其它的都變了2、構造繼承核心:使用父類(lèi)的構造函數來(lái)增強子類(lèi)實(shí)例,等于是復制父類(lèi)的實(shí)例屬性給子類(lèi)(沒(méi)用到原型)缺點(diǎn): 方法都在構造函數中定義, 只能繼承父類(lèi)的實(shí)例屬性和方法,不能繼承原型屬性/方法,無(wú)法實(shí)現函數復用,每個(gè)子類(lèi)都有父類(lèi)實(shí)例函數的副本,影響性能3、組合繼承組合繼承(所有的實(shí)例都能擁有自己的屬性,并且可以使用相同的方法,組合繼承避免了原型鏈和借用構造函數的缺陷,結合了兩個(gè)的優(yōu)點(diǎn),是最常用的繼承方式)核心:通過(guò)調用父類(lèi)構造,繼承父類(lèi)的屬性并保留傳參的優(yōu)點(diǎn),然后再通過(guò)將父類(lèi)實(shí)例作為子類(lèi)原型,實(shí)現函數復用缺點(diǎn):調用了兩次父類(lèi)構造函數,生成了兩份實(shí)例(子類(lèi)實(shí)例將子類(lèi)原型上的那份屏蔽了)4、寄生組合繼承核心:通過(guò)寄生方式,砍掉父類(lèi)的實(shí)例屬性,這樣,在調用兩次父類(lèi)的構造的時(shí)候,就不會(huì )初始化兩次實(shí)例方法/屬性,避免的組合繼承的缺點(diǎn)缺點(diǎn):堪稱(chēng)完美,但實(shí)現較為復雜。
一,js中對象繼承js中有三種繼承方式1.js原型(prototype)實(shí)現繼承復制代碼 代碼如下: <body> 2.構造函數實(shí)現繼承復制代碼 代碼如下: <body> 3.call , apply實(shí)現繼承復制代碼 代碼如下: <body> 二、call和apply的用法(詳細介紹)js中call和apply都可以實(shí)現繼承,唯一的一點(diǎn)參數不同,func.call(func1,var1,var2,var3)對應的apply寫(xiě)法為:func.apply(func1,[var1,var2,var3])。
JS手冊中對call的解釋?zhuān)簭椭拼a 代碼如下:call 方法 調用一個(gè)對象的一個(gè)方法,以另一個(gè)對象替換當前對象。 call([thisObj[,arg1[, arg2[, [,.argN]]]]]) 參數 thisObj 可選項。
將被用作當前對象的對象。 arg1, arg2, , argN 可選項。
將被傳遞方法參數序列。 說(shuō)明 call 方法可以用來(lái)代替另一個(gè)對象調用一個(gè)方法。
call 方法可將一個(gè)函數的對象上下文從初始的上下文改變?yōu)橛?thisObj 指定的新對象。 如果沒(méi)有提供 thisObj 參數,那么 Global 對象被用作 thisObj。
說(shuō)簡(jiǎn)單一點(diǎn),這兩函數的作用其實(shí)就是更改對象的內部指針,即改變對象的this指向的內容。這在面向對象的js編程過(guò)程中有時(shí)是很有用的。
下面以apply為例,說(shuō)說(shuō)這兩個(gè)函數在 js中的重要作用。如:復制代碼 代碼如下: function Person(name,age){ //定義一個(gè)類(lèi)this.name=name; //名字this.age=age; //年齡this.sayhello=function(){alert(this.name)};}function Print(){ //顯示類(lèi)的屬性this.funcName="Print";this.show=function(){var msg=[];for(var key in this){if(typeof(this[key])!="function"){msg.push([key,":",this[key]].join(""));}}alert(msg.join(" "));};}function Student(name,age,grade,school){ //學(xué)生類(lèi)Person.apply(this,arguments);//比call優(yōu)越的地方Print.apply(this,arguments);this.grade=grade; //年級this.school=school; //學(xué)校}var p1=new Person("卜開(kāi)化",80);p1.sayhello();var s1=new Student("白云飛",40,9,"岳麓書(shū)院");s1.show();s1.sayhello();alert(s1.funcName); 另外。
聲明:本網(wǎng)站尊重并保護知識產(chǎn)權,根據《信息網(wǎng)絡(luò )傳播權保護條例》,如果我們轉載的作品侵犯了您的權利,請在一個(gè)月內通知我們,我們會(huì )及時(shí)刪除。
蜀ICP備2020033479號-4 Copyright ? 2016 學(xué)習?shū)B(niǎo). 頁(yè)面生成時(shí)間:3.464秒