2010-05-23 2 views
1

J'ai un problème avec l'héritage que je suis en train de faire. Fondamentalement, j'ai une classe abstraite appelée LineCalculator, qui, comme il le suggère, calcule les lignes d'une équation. De là, j'hérite cette classe de base dans un LinearLineCalculator, qui calcule des lignes sur un système de coordonnées cartésiennes, et un PolarLineCalculator, qui calcule des lignes sur le système de coordonnées polaires.Comment gérer les classes de base interchangeables en Java

public abstract class LineCalculator { 

    // Begins calculating a line based on the parameters 
    protected final Path2D.Double calculateLine(...) { 
    } 

    // Takes in an X value, does something with it, 
    // and returns the resulting X and Y values 
    protected abstract double[] handlePoint(double x); 
} 

Ainsi LinearLineCalculator calcule uniquement la valeur de Y correspondant à une équation, alors que PolarLineCalculator serait calculer le rayon à partir de l'équation et la valeur de X, et convertir en coordonnées polaires (dans ce cas, X agit comme θ, en degrés ou radians).

LineCalculator puis calcule la ligne dans une sorte de «libre pour tous», où les threads calculant la ligne prennent et calculent les valeurs X et Y aussi vite qu'ils le peuvent et les signalent à la classe de base. La classe de base traite ensuite de la construction de la ligne à partir des données calculées par les threads. Mon problème est que j'ai implémenté une version modifiée, où elle est calculée de manière séquentielle, où la classe de base bloque sur chaque thread jusqu'à ce qu'il obtienne la première valeur. Ensuite, il attend la deuxième valeur ordonnée, et ainsi de suite, lui permettant de construire la ligne à la volée.

Ce modèle d'héritage fonctionne parfaitement, parce que j'ai été capable de modifier la classe de base sans modifier aucun des héritiers et que cela fonctionne encore. Mais je veux être capable de changer les implémentations de manière interchangeable, par exemple pour certaines lignes, calculer le style "libre pour tous", et pour certaines lignes, le calculer de manière séquentielle.

Ma question est est-il un motif ou un dessin qui me permet de changer la mise en œuvre de la classe de base, mais garde le super implémentation de la classe sans violer le principe SEC?

Répondre

6

Semble à moi comme vous voulez vraiment la composition, pas nécessairement l'héritage.

Je disposerais d'une interface Calculatrice, avec des implémentations Rectangulaires et Polaires. Donnez à la classe qui fait le calcul une référence Calculatrice que vous initialisez dans son constructeur. Cela vous permet d'échanger facilement l'implémentation. Vous aurez également besoin d'une CalculatorFactory.

+0

J'aime cette idée, mais je suis un peu confus quant aux raisons pour lesquelles j'aurais besoin d'une usine. Ne pourrais-je pas utiliser quelque chose comme 'new new LineConstructor (new PolarCalculator())'? – mgbowen

+2

Vous pouvez, mais vous serez lié à n'importe quelle classe que vous créez "nouveau". Une usine ou, mieux encore, une solution d'injection de dépendance vous permet de changer de configuration plutôt que de réécrire du code. – duffymo

+1

Ah, c'est logique. Merci, votre réponse fonctionnera parfaitement! – mgbowen

Questions connexes