# Unklarheiten beim State Pattern



## 0x10FE149 (15. Sep 2010)

hi leute 

ich bin gerade dabei mir das state pattern anzusehen und bin auf ein paar unklarheiten gestoßen... 

also angenommen wir haben die basisklasse state welche 3 methoden bereitstellt

```
public abstract void show();
public abstract void hide();
public abstract Data getData();
```
von der klasse state wird 3 mal abgeleitet (ConcreteStateA, ConcreteStateB, ConcreteStateC). alle abgeleiteten klassen implementieren die 3 abstracten methoden auf verschiedene weise. so weit so gut. was nun wenn zb ConcreteStateC eine methode setData(Data data) bräuchte, welche aber in den beiden anderen zuständen keine verwendung findet???

in der klasse in der das state pattern zum einsatz kommt werden die verschiedenen zustände ja nur als member vom typ state gehalten also:

```
private State current_state_ = null;
private State state_a_       = ConcreteStateFactory.createConcreteStateA();
private State state_b_       = ConcreteStateFactory.createConcreteStateB();  
private State state_c_       = ConcreteStateFactory.createConcreteStateC();
```

mir fallen 2 verschiedene möglichkeiten ein das oben beschriebe problem zu lösen...

1.) man castet: ((ConcreteStateC)current_state).setData(data); -> nachteil man muss die klasse ConcreteStateC importieren. somit wird das prinzip "stützen Sie sich auf abstraktionen und nicht auf konkrete klassen" welches durch die abstractFactory vertreten wird verletzt...

2.) man schreibt die methode setData(Data data) in die basisklasse -> nachteil man hat leere methodenrümpfe in 2 klassen...

beide möglichkeiten sagen mir nicht wirklich zu... 

hat jemand ideen/erfahrungen?

danke im voraus


----------



## SlaterB (15. Sep 2010)

mit einer abstrakten Basisklasse gehts es etwas kürzer, statt neu
> public abstract void setData(Data data);
schreibe
> public void setData(Data data) {}

dann kann StateC die Methode überschreiben, die anderen müssen gar nix machen

-----

auf Interface betrachtet bleibt das Problem natürlich bestehen, so ist das immer mit gemeinsamen Schnittstellen, die nicht alle Unterklassen erfüllen,
da gibt es keine (bessere als genannte) Patentlösung (in Java),

in Swing gibt es beispielsweise MouseListener mit zig Methoden, die man oft gar nicht alle braucht,
um die dann nicht immer implementieren zu müssen kann man extra von MouseAdapter erben:

```
public abstract class MouseAdapter implements MouseListener {
    /**
     * Invoked when the mouse has been clicked on a component.
     */
    public void mouseClicked(MouseEvent e) {}

    /**
     * Invoked when a mouse button has been pressed on a component.
     */
    public void mousePressed(MouseEvent e) {}

    /**
     * Invoked when a mouse button has been released on a component.
     */
    public void mouseReleased(MouseEvent e) {}

    /**
     * Invoked when the mouse enters a component.
     */
    public void mouseEntered(MouseEvent e) {}

    /**
     * Invoked when the mouse exits a component.
     */
    public void mouseExited(MouseEvent e) {}
}
```

das Problem hat übrigens mit keinem Pattern etwas zu tun, falls du nicht die Polymorhpie an sich meinst,

-----

benenne die Unterklassen lieber kürzer StateA, StateB, StateC +StateFactory.createStateA(), nicht überall 'Concrete'

verwende keine _ in normalen Variablennamen


----------



## 0x10FE149 (15. Sep 2010)

wow das gib ja schnell!!!

ha, wer hätte das gedacht, die lösung ist ja trivial... 

@ namenskonvention: war nur ein fiktives beipiel das ich mir gerade ausgedacht habe... 
@ _ : war mal codingstandart, hat sich so eingeprägt... 

danke vielmals


----------

