Maison > Article > interface Web > Programmation orientée objet JavaScript (implémentation de l'héritage)
De nombreux langages OO prennent en charge deux méthodes d'héritage : l'héritage d'interface et l'héritage d'implémentation. L'héritage d'interface hérite uniquement des signatures de méthodes, tandis que l'héritage d'implémentation hérite des méthodes réelles. Comme mentionné précédemment, l'héritage d'interface n'est pas possible dans ECMAScript puisque les fonctions n'ont pas de signature. ECMAScript ne prend en charge que l'héritage d'implémentation, et son héritage d'implémentation repose principalement sur la chaîne de prototypes. Ici, nous expliquons principalement l'héritage de chaîne de prototypes, le constructeur emprunté, l'héritage combiné, l'héritage de prototype, l'héritage parasitaire, l'héritage de combinaison parasite, etc.
1. Chaîne de prototypes
ECMAScript décrit le concept de chaîne de prototypes et utilise la chaîne de prototypes comme méthode principale pour implémenter l'héritage. L'idée de base est d'utiliser des prototypes pour permettre à un type référence d'hériter des propriétés et des méthodes d'un autre type référence. Passons brièvement en revue la relation entre les constructeurs, les prototypes et les instances : chaque constructeur possède un objet prototype, l'objet prototype contient un pointeur vers le constructeur et l'instance contient un pointeur interne vers l'objet prototype. Alors, que se passe-t-il si nous rendons l’objet prototype égal à une instance d’un autre type ? Évidemment, l'objet prototype contiendra à ce moment un pointeur vers un autre prototype et, par conséquent, l'autre prototype contient également un pointeur vers un autre constructeur. Si un autre prototype est une instance d'un autre type, alors la relation ci-dessus est toujours valable, et ainsi de suite, couche par couche, une chaîne d'instances et de prototypes est formée. C'est le concept de base de ce qu'on appelle la chaîne de prototypes.
function Person(){ this.name=”defaultName”; } Person.property.doAction=function(){ alert(“talk”); } function Student(){ this.age=5; } Student.property=new Person(); Student.property.doSome=function(){ alert(“ homework”); }
Bien que la chaîne de prototypes soit très puissante et puisse être utilisée pour implémenter l'héritage, elle présente également quelques problèmes. Le principal problème vient des prototypes contenant des valeurs de type référence. Vous vous souvenez peut-être encore que nous avons introduit plus tôt que les propriétés du prototype contenant des valeurs de type référence seront partagées par toutes les instances et c'est pourquoi les propriétés doivent être définies dans le constructeur plutôt que dans l'objet prototype ; Lorsque l’héritage est implémenté via des prototypes, le prototype devient en réalité une instance d’un autre type. Par conséquent, les attributs de l'instance d'origine sont naturellement devenus les attributs du prototype actuel. Le deuxième problème avec la chaîne de prototypes est que lors de la création d'une instance d'un sous-type, vous ne pouvez pas transmettre de paramètres au constructeur du supertype. En fait, il faut dire qu'il n'existe aucun moyen de transmettre des paramètres au constructeur d'un supertype sans affecter toutes les instances d'objet. Pour cette raison, et pour les problèmes qui viennent d'être abordés avec les prototypes contenant des valeurs de type référence, les chaînes de prototypes seules sont rarement utilisées dans la pratique.
2. Constructeur d'emprunt
Dans le processus de résolution des problèmes causés par la présence de valeurs de type de référence dans les prototypes, les développeurs ont commencé à utiliser une méthode appelée constructeur d'emprunt (vol de constructeur) technique (parfois appelée faux objets ou héritage classique). L'idée de base de cette technique est assez simple, elle consiste à appeler le constructeur de supertype à l'intérieur du constructeur de sous-type. N'oubliez pas que les fonctions ne sont rien d'autre que des objets qui exécutent du code dans un environnement spécifique, donc en utilisant les méthodes apply() et call() vous pouvez également exécuter des constructeurs sur (dans le futur) des objets nouvellement créés.
function Person(name){ this.name=name; } Person.property.doAction=function(){ alert(“talk”); } Person.property.showName=function(){ alert(this.name); } function Student(){ Person.call(this,name); this.age=5; }
Si vous empruntez simplement le constructeur, vous ne pourrez pas éviter les problèmes du modèle de constructeur - Les méthodes sont toutes définies dans le constructeur, donc la réutilisation des fonctions est hors de question . De plus, les méthodes définies dans le prototype du supertype sont également invisibles pour les sous-types. Par conséquent, tous les types ne peuvent utiliser que le modèle constructeur. Compte tenu de ces problèmes, la technique de l’emprunt aux constructeurs est rarement utilisée seule.
3. Héritage combiné
L'héritage combiné, parfois également appelé héritage pseudo-classique, fait référence à la combinaison de la chaîne de prototypes et de l'emprunt de techniques de constructeur pour tirer parti du meilleur des deux. L'idée derrière cela est d'utiliser la chaîne de prototypes pour obtenir l'héritage des propriétés et des méthodes du prototype, et pour obtenir l'héritage des propriétés d'instance en empruntant des constructeurs. De cette manière, la réutilisation des fonctions est réalisée en définissant des méthodes sur le prototype, et chaque instance est garantie d'avoir ses propres attributs.
function Person(name){ this.name=name; this.loves=[“sing”,”paly games”] } Person.property.showLoves=function (){ alert(this.lovers); } function Student(name,age){ Person.class(this,name); This.age=age; } Student.property=new Person(); Student.property.constructor=Student; Student.property.showName=function(){ alert(this.name); }
L'héritage combiné évite les défauts des chaînes de prototypes et des constructeurs empruntés, combine leurs avantages et devient le modèle d'héritage le plus couramment utilisé en JavaScript. De plus, instanceof et isPrototypeOf() peuvent également être utilisés pour identifier des objets créés sur la base d'un héritage combiné.
4. Héritage prototypique
function object(o){ function F(){} F.prototype = o; return new F(); }
Quand il n'est pas nécessaire de faire de grands efforts pour créer un constructeur, mais que vous souhaitez simplement conserver un objet similaire à un autre objet, l'héritage prototypique est pleinement capable. Mais n'oubliez pas que les propriétés contenant des valeurs de type référence partageront toujours la valeur correspondante, tout comme si vous utilisiez le modèle prototype.
5. Héritage combiné parasite
L'héritage combiné parasite signifie hériter de propriétés en empruntant des constructeurs et en héritant de méthodes via la forme hybride de la chaîne de prototypes. L'idée de base derrière
est la suivante : il n'est pas nécessaire d'appeler le constructeur du supertype pour spécifier le prototype du sous-type. Tout ce dont nous avons besoin est de rien de plus qu'une copie du prototype du supertype
. Essentiellement, vous utilisez l'héritage parasite pour hériter du prototype du supertype, puis attribuez le résultat au prototype du sous-type . Le modèle de base de l’héritage combinatoire parasitaire est le suivant.function inheritPrototype(subType, superType){ var prototype = object(superType.prototype); //创建对象 prototype.constructor = subType; //增强对象 subType.prototype = prototype; //指定对象 }
个参数:子类型构造函数和超类型构造函数。在函数内部,第一步是创建超类型原型的一个副本。第二步是为创建的副本添加constructor 属性,从而弥补因重写原型而失去的默认的constructor 属性。最后一步,将新创建的对象(即副本)赋值给子类型的原型。这样,我们就可以用调用inheritPrototype()函数的语句,去替换前面例子中为子类型原型赋值的语句了。
集寄生式继承和组合继承的优点与一身,是实现基于类型继承的最有效方式。
以上就是JavaScript面向对象编程(继承实现方式)的内容,更多相关内容请关注PHP中文网(www.php.cn)!