Concepts de base de l'héritage et de la synthèse
Héritage: une nouvelle classe peut être construite sur la base d'une classe existante. Hériter des classes existantes peut réutiliser les méthodes et les domaines de ces classes. Sur cette base, de nouvelles méthodes et domaines peuvent être ajoutés pour étendre les fonctions de la classe.
Synthèse: la création de l'objet original dans une nouvelle classe est appelée synthèse. De cette façon, vous pouvez réutiliser le code existant sans modifier son formulaire.
1. Syntaxe héréditaire
Le mot-clé étend indique que la nouvelle classe est dérivée d'une classe existante. Une classe existante est appelée une classe parent ou une classe de base, et une nouvelle classe est appelée sous-classe ou une classe dérivée. Par exemple:
Élève de classe étend la personne {}L'élève de classe hérite de la personne. La classe de personne est appelée classe parent ou classe de base, et la classe d'élève est appelée sous-classe ou classe dérivée.
2. Synthèse de la synthèse
La synthèse est relativement simple, qui est de créer une classe existante dans une classe.
classe étudiante {chien chien;}Style ascendant
1. Concepts de base
Le rôle de l'héritage réside dans la réutilisation du code. Étant donné que l'héritage signifie que toutes les méthodes de la classe parent peuvent également être utilisées dans les sous-classes, les messages envoyés à la classe parent peuvent également être envoyés à la classe dérivée. S'il y a une méthode EAT dans la classe de personne, il y aura cette méthode dans la classe étudiante, ce qui signifie que l'objet étudiant est également un type de personne.
classe de classe {public void Eat () {System.out.println ("manger");} static void show (personne p) {p.eat ();}} public class étudiant étend la personne {public static void main (string [] args) {étudiant s = new student (); personne.show (s); // ①}}【Résultats de l'opération】:
manger
La méthode Show définie en personne est utilisée pour recevoir des poignées de personne, mais à ①, elle reçoit une référence à l'objet étudiant. En effet, l'objet étudiant est également un objet de personne. Dans la méthode Show, la poignée (référence à l'objet) peut être un objet personne et un objet de classe dérivé de personne. Ce comportement de convertir les poignées des étudiants en poignées de personne devient un modèle ascendant.
2. Pourquoi avez-vous besoin de tracer la forme?
Pourquoi voulez-vous ignorer délibérément le type d'objet qui l'appelle lors de l'appel Eat? Si vous créez la méthode de spectacle, obtenez simplement la poignée de l'élève, il semble plus intuitif et facile à comprendre, mais cela rendra chaque nouvelle classe dérivée de la classe de la classe Implémente sa propre méthode de spectacle:
Valeur de classe {private int count = 1; valeur privée (int count) {this.count = count;} public statique final valeur v1 = nouvelle valeur (1), v2 = nouvelle valeur (2), v3 = nouvelle valeur (3);} classe de classe {public void eat (valeur v) {System.out.println ("Person.eat ()");}} Classe Teacher Exproprié {System.out.println ("Teacher.Eat ()");}} classe Étudiant étend la personne {public void Eat (Value V) {System.out.println ("Student.Eat ()");}} public class upcastingdemo {public static static show (Student S) {s.eat (value.v1);} public static static show (professeur T) {t.eat (value.v1);} public static void show (personne p) {p.eat (value.v1);} public static void main (string [] args) {élève s = new student (); enseignant t = new enseignUn défaut évident dans cette approche est qu'il est nécessaire de définir des méthodes étroitement liées à la classe dérivée de chaque classe de personne, ce qui entraîne beaucoup de code en double. D'un autre côté, si vous oubliez la surcharge de la méthode, vous ne signalerez pas d'erreur. Les trois méthodes montrent dans l'exemple ci-dessus peuvent être fusionnées en une seule:
public static void show (personne p) {p.eat (value.v1);} Liaison dynamique
Lors de l'exécution des spectacles, le résultat de sortie est Student.Eat (). C'est en effet le résultat souhaité, mais il ne semble pas être exécuté sous la forme que nous espérions. Jetons un coup d'œil à la méthode de spectacle:
public static void show (personne p) {p.eat (value.v1);}Il reçoit une poignée de personne. Lorsque vous effectuez des spectacles, comment sait-il que la personne gère les points vers un objet étudiant au lieu d'un objet enseignant? Le compilateur n'a aucun moyen de le savoir, ce qui implique le problème de contrainte à expliquer ensuite.
1. Méthode Call Binding
La connexion d'une méthode et le même corps de méthode ensemble est appelée liaison. Si la liaison est effectuée avant l'exécution, elle s'appelle "la liaison précoce". Dans l'exemple ci-dessus, lorsqu'il n'y a qu'une seule manche, le compilateur ne sait pas quelle méthode appeler. Java implémente un mécanisme d'appel de méthode qui peut déterminer le type d'un objet pendant le fonctionnement, puis appeler la méthode correspondante. Cette liaison basée sur le type de l'objet est appelée liaison dynamique pendant le fonctionnement. À moins qu'une méthode ne soit déclarée finale, toutes les méthodes de Java sont liées dynamiquement.
Utilisez une image pour représenter la relation d'héritage de la forme ascendante:
Dans le code, il est résumé comme:
Shapes=newShape();
Selon la relation d'héritage, il est légal d'attribuer la poignée de l'objet cercle créé à une forme, car le cercle appartient à une forme.
Lorsque l'une des méthodes de classe de base est appelée:
Shapes=newShape();
À l'heure actuelle, Circle.Draw () est appelé, ce qui est dû à la liaison dynamique.
classe de classe {void Eat () {} void dispens () {}} classe Boy étend la personne {void eat () {System.out.println ("boy.eat ()");} void dispel () {System.out.println ("boy.speak ()");}} classe Girl étend la personne {Void Eat () {System.out.println ("girl.eat ()");}} classe publique Personnes {Public Static Person Randperson () {Switch ((int) (Math.Random () * 2)) {Default: Case 0: Return New Boy (); Cas 1: Return New Girl ();}} public Static Void Main (String [] args) {Person [] P = New Person [4] pour (int i = 0; <p.Length; i ++) {p [i] = randSerson (); // générer au hasard garçon ou fille} pour (int i = 0; i <p.length; i ++) {p [i] .eat ();}}}Pour toutes les classes dérivées de la personne, la personne établit une interface générale et toutes les classes dérivées ont deux comportements: manger et parler. La classe dérivée remplace ces définitions et redéfinit les deux comportements. Dans la classe principale, Randperson sélectionne au hasard la poignée de l'objet Personne. ** Le style d'appel se produit dans la déclaration de retour. L'instruction ** Retour prend une poignée de garçon ou de fille et la retourne en tant que type de personne. Pour le moment, je ne sais pas de quel type il s'agit, je sais seulement que c'est une poignée d'objet de personne. Dans la méthode principale, appelez la méthode Randperson pour remplir l'objet de la personne au tableau, mais ne connaissez pas la situation spécifique. Lorsque la méthode EAT de chaque élément du tableau est appelée, la fonction de la liaison dynamique est d'exécuter la méthode redéfinie de l'objet.
Cependant, la liaison dynamique est une condition préalable, et la méthode de liaison doit exister dans la classe de base, sinon elle ne sera pas compilée et passée.
classe de classe {void Eat () {System.out.println ("personne.eat ()");}} classe Boy étend la personne {void eat () {System.out.println ("boy.eat ()");} void dispens () {System.out.println ("boy.speak ()");}} Public Class Persons {public Static Void Main () ") {Personne p = new boy (); p.eat (); p.speak (); // la méthode speak () n'est pas définie pour la personne type}}Si aucune méthode de remplacement n'est définie dans la sous-classe, la méthode de la classe parent est appelée:
Classe Person {void Eat () {System.out.println ("Person.eat ()");}} classe Boy étend la personne {} classe publique Persons {public static void main (String [] args) {personne p = new boy (); p.eat ();}}【Résultats de l'opération】:
Personne.eat ()
2. Liaison des méthodes statiques
Ajoutez le mot-clé statique aux méthodes ci-dessus et transformez-les en méthodes statiques:
classe de classe {static void eat () {System.out.println ("Person.eat ()");} static void Speak () {System.out.println ("Person.speak ()");}} classe Boy étend la personne {static void Eat () {System.out.Println ("boy.eat ()");}} STATIC VOID Speaker () {System.out.println ("boy.speak ()");}} class Girl étend la personne {static void eat () {System.out.println ("girl.eat ()");} static void dispens () {System.out.println ("girl.speak ()");}} classe publique Persons {public static personne static randperson () {commutateur. ((int) (math.random () * 2)) {par défaut: cas 0: return new boy (); cas 1: return new girl ();}} public static void main (String [] args) {personne [] p = new personne [4]; pour (int i = 0; i <p.length; i ++) {p [i] = randperson (); // boy ou girl} pour (int i] = 0; i <i <i; p.Length; i ++) {p [i] .eat ();}}} 【Résultats de l'opération】:
Personne.eat ()
Personne.eat ()
Personne.eat ()
Personne.eat ()
Résultats de l'observation: Pour les méthodes statiques, quelle que soit l'objet sous-classe auquel la classe parent fait référence, la méthode de la classe parent est appelée.
Formule mnémonique
- Méthode statique: la méthode statique examine la classe parentale
- Méthodes non statiques: les méthodes non statiques examinent les sous-classes
Résumer
Ce qui précède est tout le contenu de l'interprétation détaillée par cet article du concept de l'héritage Java, et j'espère que cela sera utile à tout le monde. Les amis intéressés peuvent continuer à se référer à d'autres sujets connexes sur ce site. S'il y a des lacunes, veuillez laisser un message pour le signaler. Merci vos amis pour votre soutien pour ce site!