Interface Probleme mit Observer

musti2304

Mitglied
Hallo Leute,

ich habe in eine der Musterklausuren (siehe angehängtes Bild) folgende Lösung als Musterlösung bekommen.
Es sind 4 Klassen:
Java:
public class Counter {

	/*Was genau passiert hier und was bewirkt es?*/
    private Observer observer;
	
	//Ist mir klar
    private int value = 0;

	//Ist mir klar
    public void increment() { 
        //Ist mir klar
		this.value++;
		/*Was genau passiert hier im if-Block und was bewirkt es?*/
	if ( this.observer != null ) {
	    this.observer.newValue(this);
		}
    }
	/*Warum übergibt man die Parameter so?*/
    public void setObserver(Observer observer) {
        this.observer = observer;
    }
	
    public int get() { return this.value; }
}
Java:
public interface Observer {

	/* Was passiert wenn man eine Klasse als Parameter übergibt?
	 * Warum macht man das?
	 */
	
    public void newValue(Counter counter);
}
Java:
public class ObserverImpl implements Observer {

    public void newValue(Counter counter) { 
		/* Was passiert bei counter.get() ?
		 *
		 */
        System.out.println("Neuer Zaehlerstand: " + counter.get());
    }
}
Java:
public class Main {

    public static void count(Counter c) {
	for (int i=0 ; i<5; i++) {
		/*Was genau passiert hier und was bewirkt es?*/
	    c.increment();
	}
    }

    public static void main(String[] args) {
        //Ist mir klar
		Counter c = new Counter();

		/* Was genau passiert hier und was bewirkt es?
		 * Vor allem mit new im Parameter? Warum?
		 */
		c.setObserver(new ObserverImpl());
		
        count(c);
    }
}

So es muss nichts(!) gelöst werden. Die Lösung steht da. Allerdings kann ich nicht nachvollziehen was gemacht wurde. Was ich nachvollziehen will kann man in den Kommentaren lesen.
Da ich meine Klausur in zwei Wochen schreibe wäre ich euch sehr dankbar, wenn mir das einer erklären könnte.
Mir ist nur nicht klar wie die Objekte und Interfaces miteinander kommunizieren
Ich weiß jede hilfreiche Antwort zu schätzen.

Vielen Dank :)

Aufgabe.jpg
 

musti2304

Mitglied
Hi Im Internet gibts mit einfacher Suche relativ viele Treffer, die das Observer-Pattern gut erklären. u.a wird es auch in der Insel erklärt: Rheinwerk Computing :: Java ist auch eine Insel - 10 Architektur, Design und angewandte Objektorientierung. Wenn du das durchgelesen hast, dann wird dir das Pattern sicher verständlicher sein.

Hallo knilch,

es geht in dieser Aufgabe aber nicht um die von Java bereitgestellte Schnittstelle, also nicht um java.util.Observer.
Ich will nur (wie oben bereits erwähnt) wissen, was in den einzelnen Schritten "in Worten" so passiert.
Beispiel: Es wird die main-Methode aufgerufen. Dann ein Objekt Counter erzeugt. Dann.... usw. und zwar nur an den Stellen die kommentiert sind.
 
Zuletzt bearbeitet:

knilch

Bekanntes Mitglied
Hi,
Das Beispiel, dass in der Insel erklärt wurde, ist mit dem Observer- Pattern von Java implementiert. Das stimmt, aber allgmein, ist das Observer-Pattern, das du hier zeigst, ähnlich. Es geht darum dass eine Änderung an viele (also an all die Instanzen) mitgeteilt wird, die an der Änderung interessiert sind.
Ich versuch mal etwas zu deinen Fragen zu schreiben:
Java:
public class Main {
    public static void count(Counter c) {
        for (int i=0 ; i<5; i++) {
            /*Was genau passiert hier und was bewirkt es?*/
            c.increment();
            // ist eigentlich klar, hier wird auf der Instanz c der Klasse Counter die Methode increment() 5 x aufgerufen...
        }
    }
    public static void main(String[] args) {
        //Ist mir klar
        Counter c = new Counter();

        /* Was genau passiert hier und was bewirkt es?
         * Vor allem mit new im Parameter? Warum?
         */
        c.setObserver(new ObserverImpl());
        // Es geht darum, dass alle, die interessiert sind, wenn die Methode c.increment(); ausgeführt wird, davon mitbekommen. 
        // Da Observer nur das Interface ist (und ObserverImpl dieses Interface implementiert) wird eine neue Instanz von ObserverImpl
        // In der Instanz c der Klasse Counter registiert. 
        // D.h. Wenn sich in c etwas ändert, dann wird die Methode newValue(...) ausgeführt.    
        count(c);
    }
}
Java:
public interface Observer {
    /* Was passiert wenn man eine Klasse als Parameter übergibt?
    // was meinst du damit?
    
    /*
    * Warum macht man das?
    */     
    public void newValue(Counter counter);
    // Wie geschrieben, Observer ist ein Interface. Im Interface wird eine oder mehrere Methode deklariert. Alle Klassen, die dieses
    // Inteface implementieren, müssen dann die Methode(n) die im Interface deklariert wurden, definieren (d.h. in diesen Klassen muss
    // dann der Code geschrieben werden, der ausgeführt werden soll, wenn newValue ausgerufen wird). 
    // In deinem Beispiel implementiert die Klasse ObserverImpl dieses Interface, und damit wird in der Methode newValue(){..}
    // dieser Klasse der Code geschrieben, der dann ausgeführt wird wenn newValue(..) aufgerufen wird.
}
Java:
public class ObserverImpl implements Observer {
    // diese Klasse implementiert nun das Interface Observer. Somit wird in der Methode newValue(...) {...} der Code geschrieben, 
    // der dann ausgeführt wird.
    public void newValue(Counter counter) {
        /* Was passiert bei counter.get() ?
         */
        System.out.println("Neuer Zaehlerstand: " + counter.get());
        // ist eigentlich klar, es wird die Methode get() von der Instanz counter aufgerufen und auf der Console ausgegeben
    }
}
Java:
public class Counter {
    /*Was genau passiert hier und was bewirkt es?*/
    private Observer observer;
    // Variable deklarieren ... 

    //Ist mir klar
    private int value = 0;

    //Ist mir klar
    public void increment() {
        //Ist mir klar
        this.value++;
        /*Was genau passiert hier im if-Block und was bewirkt es?*/
        if ( this.observer != null ) {
            this.observer.newValue(this);
        }
// hier wird nun auf die Methode newValue(this) der Instanz observer aufgerufen, als Argument wird: this mitgegeben
// (da aber in main() {... c.setObserver(new ObserverImpl());...} eine Instanz von ObserverImpl erzeugt wird,
// wird die implementierte Methode newValue(this) der Klasse ObserverImpl aufgerufen. 
// (Observer ist ja ein interface --> aus einem interface kann nie eine Instanz erzeugt werden, somit kann auch die Methode: newValue(...) von Observer nie aufgerufen werden )    
// this --> (sollte eigentlich klar sein, eine Instanz von Counter .d.h. die Instanz c die in main() erstellt wurde).
    }
    /*Warum übergibt man die Parameter so?*/
    public void setObserver(Observer observer) {
        this.observer = observer;
    }
    // hier wird nun der Varible this.observer die Instanz übergeben. d.h. mit new ObserverImpl
    //wird eine neue Instanz erzeugt und diese dann der Variable observer zugewiesen:
    //c.setObserver(new ObserverImpl());
    

    public int get() { return this.value; }
}
 

Saheeda

Top Contributor
@knilch

Im Insel-Link sind zwei verschiedene Implementierungen aufgeführt: So ähnlich wie von musti2304 und über Event-Listener.
Mir erscheint es irgendwie einfacher/intuitiver, mit Events zu arbeiten. Ist das nur Geschmackssache oder was ist hier best-practise?
 

knilch

Bekanntes Mitglied
@knilch

Im Insel-Link sind zwei verschiedene Implementierungen aufgeführt: So ähnlich wie von musti2304 und über Event-Listener.
Mir erscheint es irgendwie einfacher/intuitiver, mit Events zu arbeiten. Ist das nur Geschmackssache oder was ist hier best-practise?
Es kommt immer auf den Context drauf an.
Mit dem Observer-Pattern werden alle die an einer Aktualisierung interessiert sind, benachrichtigt. d.h. Wenn die Änderung stattgefunden hat, wird die an die Interessenten raportiert. Im Gegensatz zu den Events, bzw. Listeners, hier schauen die Interessierten selbst, ob eine Änderung stattgefunden hat.
Vielleicht hilft dir das hier weiter...https://doanduyhai.wordpress.com/2012/08/04/design-pattern-the-asynchronous-dispatcher/
 
Zuletzt bearbeitet:

Neue Themen


Oben