Auf änderung horchen

Gnoccy

Mitglied
Nabend,

ich hätte mal eine frage. Und zwar arbeite ich zur Zeit an einem Programm, für das es notwendig ist, dass ein Objekt einer Klasse mitbekommt, wenn sich an einem Array eines Objektes einer anderen Klasse etwas verändert, so das die erste Klasse darauf reagieren kann.
Konkret geht es darum, dass sich auf meiner Oberfläche die Beschriftung einiger Button ändert, wenn in besagtem Array eine änderung stattfindet.
Dies soll aber geschehen, ohne dass die zweite Klasse auf die erste zugreift, bzw. eine Methode der ersten Klasse ausführt. Überhaupt soll die erste Klasse nirgendwo in der zweiten auch nur erwähnt werden.

Ich hoffe, es ist verständlich, was ich meine. Das ist eines der ersten etwas komplexeren Programme die ich von Grund auf selbst entwickle. Bisher habe ich nur Programme vervollständigt, bei denen die Oberfläche schon fertig war, und ich nur einzelne Methoden schreiben musste.


Würde mich über hilfe freuen,
Gruß Gnoccy
 
S

Spacerat

Gast
Auf jeden Fall muss das Array in einer Klasse gekapselt werden und alle Änderungen über Methoden vorgenommen werden (z.B. per [c]setElement(int index, Object value)[/c]), in welcher Listener über diese Änderungen informiert werden könnten. Schon ist man relativ schnell bei der Implementation einer eigenen ArrayList, was aber bereits schon wieder völlig überzogen wäre. Eine generische Klasse [c]Array<T>[/c] wäre evtl. sinnvoll.
 

Gnoccy

Mitglied
Ja, es ist nur ein Array. Verstehe ich das richtig, ich brauche eine eigene Klasse, in der sich nur das Array befindet? Und wie genau funktioniert das mit den Listenern? Wie gesagt, das ist relativ neu für mich und ich kannte Listener bisher nur so, dass sie einen Button o.ä. beobachtet haben, aber keine Variable...
 
M

Marcinek

Gast
Naja du hast eine Liste mit möglichen Interessenten für die Änderungsinfo.

Und da können sich bestimmte Objekte hinzufügen.

Beispiele hierfür findest du überal im Web oder in einem besseren Java Buch.
 
S

Spacerat

Gast
Ganz banal geht das etwa so:
Java:
import java.util.Arrays;
import java.util.HashSet;
import java.util.Set;


public class ObservableArray<T>
implements Mutable
{
	private final Set<MutableListener> listener = new HashSet<MutableListener>();
	private final Object[] data;

	public ObservableArray(int length)
	{
		data = new Object[length];
	}

	public void addMutableListener(MutableListener ml)
	{
		listener.add(ml);
	}

	public void removeMutableListener(MutableListener ml)
	{
		listener.remove(ml);
	}

	public T setElement(int index, T value)
	{
		checkRange(index);
		@SuppressWarnings("unchecked")
		T rc = (T) data[index];
		data[index] = value;
		synchronized(listener) {
			for(MutableListener ml : listener) {
				ml.objectUpdated(this);
			}
		}
		return rc;
	}

	@SuppressWarnings("unchecked")
	public T getElement(int index)
	{
		checkRange(index);
		return (T) data[index];
	}

	public int length()
	{
		return data.length;
	}

	public int hashCode()
	{
		return Arrays.hashCode(data);
	}

	public boolean equals(Object obj)
	{
		if(this == obj) {
			return true;
		}
		if(obj instanceof ObservableArray) {
			return Arrays.equals(data, ((ObservableArray<?>)obj).data);
		}
		return false;
	}

	private void checkRange(int index)
	{
		if(index < 0 || index >= data.length) {
			throw new ArrayIndexOutOfBoundsException(index);
		}
	}
}

/*public */interface Mutable
{
	void addMutableListener(MutableListener ml);
	void removeMutableListener(MutableListener ml);
}

/*public */interface MutableListener
{
	void objectUpdated(Mutable m);
}
Die Interfaces sollten aber nach Möglichkeit public sein, ging nur im KSKB nicht, sonst wär es nicht kompilierbar. Schöner geht's natürlich mit einer EventQueue (EDT), einem zusätzlichem Thread, in welchem sich die Problematik mit der Endlosschleife verhindern lässt, indem man feststellt, ob eine Änderung innerhalb des EDT vorgenommen wurde und evtl. eine entsprechende Exception wirft.
 


Schreibe deine Antwort... und nutze den </> Button, wenn du Code posten möchtest...

Ähnliche Java Themen

Neue Themen


Oben