1. Classe de base commune
Aujourd'hui, nous allons profiter d'un assortiment de sujets intéressants. Vous vous souvenez quand nous avons introduit la ChessItem
classe de base pour simplifier toutes les classes représentant des pièces d'échecs ? Je l'espère 🙂
Imaginez maintenant que chaque pièce a une draw()
méthode qui gère son dessin à l'écran. Vous appelez la draw()
méthode et la pièce se dessine à ses coordonnées actuelles. Il serait pratique de déplacer cette méthode vers la classe de base.
Si la draw()
méthode était dans la classe de base ChessItem, alors nous pourrions la remplacer dans les classes de pièces et écrire un code élégant comme celui-ci :
class ChessBoard
{
public void drawAllChessItems()
{
// Add the pieces to the list
ArrayList<ChessItem> items = new ArrayList<ChessItem>();
items.add(new King());
items.add(new Queen());
items.add(new Bishop());
// Draw them regardless of their type
for(ChessItem item: items)
{
item.draw();
}
}
}
En introduisant la ChessItem
classe de base, nous avons pu grandement simplifier le code : il n'est pas nécessaire d'appeler les méthodes de chaque classe séparément, on peut facilement stocker tous les objets dans une seule collection, etc.
Mais voici une question intéressante : que doit dessiner à l'écran la draw()
méthode déclarée directement dans la classe ? ChessItem
Après tout, il n'y a pas une telle pièce aux échecs, donc il n'y a rien à tirer.
C'est exactement ça. De plus, cela n'a aucun sens de créer ChessItem
directement des objets. Ce n'est pas une pièce d'échecs, mais plutôt une abstraction - une classe que nous avons créée pour notre commodité. C'est ainsi que fonctionne l'abstraction en POO : nous déplaçons les données et méthodes importantes (celles partagées par tous les morceaux) vers une classe de base, et conservons leurs différences dans des classes descendantes distinctes.
2. Classes abstraites
Pour de telles situations, Java a un type spécial de classe : la classe abstraite . Ils sont conçus pour permettre aux programmeurs de travailler plus facilement avec des classes similaires et de réduire la quantité de code dupliqué qu'ils contiennent.
Voici trois choses à savoir sur les classes abstraites.
Méthode sans implémentation
Une classe abstraite peut avoir une déclaration de méthode sans implémentation. C'est exactement ce qui rend la méthode abstraite. Le corps de la méthode est simplement remplacé par un point-virgule. Et avant le nom de la méthode, nous écrivons le abstract
mot-clé. Exemple:
public abstract class ChessItem
{
public int x, y; // Coordinates
private int value; // The piece's value
public int getValue() // Ordinary method that returns value field
{
return value;
}
public abstract void draw(); // Abstract method. The implementation is missing.
}
Classe abstraite
Chaque méthode sans implémentation est marquée avec le mot-clé abstract. Si une classe a ne serait-ce qu'une seule méthode abstraite, la classe est également marquée avec le abstract
mot-clé.
Interdire la création d'objets
Vous ne pouvez pas créer d'objets d'une classe abstraite . Un tel code ne compilera tout simplement pas.
Code | Description |
---|---|
|
Ce code ne compile pas : |
|
Mais tu peux faire ça |
Héritage d'une classe abstraite
Si votre classe hérite d'une classe abstraite, vous devez remplacer toutes les méthodes abstraites héritées, c'est-à-dire que vous devez écrire une implémentation pour elles. Sinon, votre classe elle-même devra également être déclarée abstraite.
Si une classe a ne serait-ce qu'une seule méthode non implémentée déclarée directement ou héritée d'une classe parente, alors la classe est considérée comme abstraite.
Et pourquoi tout cela est-il nécessaire ? Pourquoi les classes abstraites sont-elles nécessaires ? N'est-il pas possible d'utiliser des modèles ordinaires à la place ? Et au lieu de méthodes abstraites, ne pourrions-nous pas simplement écrire deux accolades vides comme corps de la méthode ?
Nous pourrions. Mais ces restrictions s'apparentent au private
modificateur. Nous utilisons le mot clé private pour empêcher délibérément d'autres programmeurs d'accéder directement aux données et pour les forcer à n'utiliser que nos méthodes publiques lors de l'écriture de leurs classes.
C'est la même chose avec les classes abstraites. L'auteur d'une classe abstraite ne veut pas que les objets de la classe soient créés. Au lieu de cela, l'auteur s'attend à ce que les méthodes abstraites soient héritées de la classe abstraite, puis remplacées.
L'avantage de cette approche est évident dans les grands projets. Plus vous avez de classes, plus vous devez définir clairement leurs rôles. Vous verrez l'avantage de cette approche dans un avenir proche. Tout passe par là.
GO TO FULL VERSION