9
votes

Conception à l'aide de la composition et des interfaces en Java

J'ai conçu ce qui suit pour un problème:

class Animal {
 // ...
}
class Guppy extends Animal { ... }
class Pigeon extends Animal { ... }
class Ram extends Animal implements IHorned { ... }
class Cat extends Animal implements ITailed { ... } 
class Dog extends Animal implements ITailed {
 BasicTail t = new BasicTail();
 public Object getTail() {
  return t.getTail();
 }
 public void setTail(Object in) {
  t.setTail(in);
 }
}

interface ITailed {
 public Object getTail();
 public void setTail(Object in);
 //...
}

class BasicTail implements ITailed {
 Object myTail;
 public Object getTail() { return myTail; }
 public void setTail(Object t) { myTail = t; }
}

interface IHorned {
 // getters and setters
}

public static void main(String[] args) {
 Animal a = getSomeAnimal();
 a.doSomething();
    // how do I check if a is horned or tailed?
}


1 commentaires

Khachik, je crois que c'est "l'instance de ihorned"


3 Réponses :


1
votes

J'ai modifié ma réponse précédente. J'ai pensé à quelque chose de beaucoup mieux. Voir la révision de ce message si vous êtes curieux.

Utiliser le modèle de spécification. Cela correspond beaucoup à la facture ici - bien plus que décorateur. Vous avez demandé à "vérifier" si un animal était cornu. Le motif de décorateur offre une transparence, tandis que dans cette situation, vous semblez demander une discrimination.

Le modèle de spécification encapsule la connaissance de la manière d'évaluer certains critères. Dans notre cas, nous voudrions quelque chose comme: xxx

Maintenant, vous pouvez définir votre hiérarchie de votre animal, mais vous voulez. La seule chose que vous avez maintenant besoin de faire est de comprendre ce que fait un animal cornu. Votre réponse à cette question passe dans la classe de spécifications. Ensuite, votre fonction principale est facile comme tarte. xxx


0 commentaires

4
votes

Je pense que vous devez éviter les configurisateurs en général. Si vous le pouvez, utilisez des objets immuables et initialiser ses données privées dans son constructeur.

Pour distinguer les animaux, j'ai utilisé un autre motif, le visiteur un. C'est verbeux, mais vous n'avez pas à tester directement quel animal vous traitez. xxx


1 commentaires

Le modèle de visiteur est effectivement souvent (comme dans ce cas) un très flexible, surtout parce qu'il évite de chèques méchants de contrôles .



9
votes

Je suggérerais ici un modèle de stratégie ici. En bref:

interface TailedAnimal {
    void moveTail();
}
interface HornedAnimal {
    void hitWithHorn();
}
class Rhinoceros() implements TailedAnimal, HornedAnimal {
    private TailedAnimal tail;  //Instantiate it somehow e.g. constructor, setter
    private HornedAnimal horn;  //Instantiate it somehow e.g. constructor, setter
    public void moveTail() {
        tail.moveTail();
    }
    public void hitWithHorn() {
        horn.hitWithHorn();
    }
}


1 commentaires

Hey, je l'ai eu en premier;). Quoi qu'il en soit, cette réponse est plus "compacte" que la mienne