Software-Entwurfsmuster

Compound-Iterator

 English version  aufwärts

Problem

Gegeben ist eine ArrayList a0, deren Einträge wiederum ArrayLists sind, die Objekte vom Typ String enthalten. Sollen nun alle diese Objekte durchlaufen werden, sind zwei Iteratoren erforderlich, die in geschachtelten Schleifen auftreten:

    public void output(ArrayList<ArrayList<String>> a0)
    {
        Iterator<ArrayList<String>> i0;
        Iterator<String> i1;
        ArrayList<String> a1;
        i0=a0.iterator();    // standard iterator of ArrayList
        while (i0.hasNext())
        {
            a1=i0.next();
            i1=a1.iterator();
            while (i1.hasNext())
                System.out.print(i1.next()+" ");
        }
    }

 

Gesucht ist nun ein zusammen­gesetzter Iterator, der die Funktion der beiden geschachtelten Iteratoren übernimmt.

Ein solcher Iterator ist ein Compound-Iterator. Ein Compound-Iterator benutzt einen Basis­iterator (im Beispiel der ArrayList-Iterator für a0) und einen Subiterator (im Beispiel der ArrayList-Iterator für a1). Ferner wird eine Funktion composeItems benötigt, um aus den beiden Cursor-Objekten der beiden Iteratoren ein Objekt zu machen, das mit next() zurück­gegeben wird (im Beispiel wird nur das Cursor-Objekt des Subiterators verwendet).

Der Compound-Iterator ist nach dem Bridge-Entwurfs­muster gebildet. Er verwendet ein Behavior, das den Basis­iterator, den Subiterator und die Funktion composeItems bereitstellt (Bild 1). Das Behavior enthält auch gleich noch eine Factory-Methode, um den so gebildeten Iterator zu erzeugen.

Bild 1: Klassendiagramm eines Compound-Iterators mit dem konkreten Behavior NestedArrayList
Bild 1: Klassendiagramm eines Compound-Iterators mit dem konkreten Behavior NestedArrayList

Nur die blau dargestellte Klasse NestedArrayList ist vom Anwender zu schreiben (siehe nächster Abschnitt). Hierzu ist lediglich ein Basis­iterator und ein Subiterator anzugeben (hier beide Male der Standard-Iterator von ArrayList) sowie eine Funktion composeItems zu implementieren, die aus den Cursor-Objekten des Basis­iterators und des Subiterators ein Rückgabe­objekt erzeugt.

Die folgenden Programm­beispiele verwenden Typ-Parameter. Die benötigten Import-Anweisungen für Iterator und ArrayList sind der Kürze halber weggelassen.

Behavior NestedArrayList

Das Behavior NestedArrayList erzeugt einen Compound-Iterator, der eine ArrayList von ArrayLists mit Einträgen vom Typ Type durchläuft. Im Konstruktor wird der Klasse die zu durch­laufende Haupt-ArrayList übergeben. Es folgen dann die drei Methoden, die in der abstrakten Basisklasse CompoundIteratorBehavior festgelegt sind.

In der Methode baseIterator wird der Basis­iterator spezifiziert, der die Haupt-ArrayList durchläuft, und in der Methode subIterator der jeweilige Subiterator, hier in Abhängigkeit von dem aktuellen Eintrag der Haupt-ArrayList. Die Methode composeItems verwendet hier nur den Eintrag der Unter-ArrayList. Die erwähnte Factory-Methode, die den fertigen Iterator zurückgibt, befindet sich in der Basisklasse CompoundIteratorBehavior.

public class NestedArrayList<Type>
extends CompoundIteratorBehavior<ArrayList<Type>, Type, Type>
{
    private ArrayList<ArrayList<Type>> a0;

    public NestedArrayList(ArrayList<ArrayList<Type>> a0_)
    {
        a0=a0_;
    }

    /** the base iterator
     */
    @Override
    public Iterator<ArrayList<Type>> baseIterator()
    {
        return a0.iterator();
    }

    /** the subiterator,
     *  o0 is the cursor object of the base iterator
     */ 
    @Override
    public Iterator<Type> subIterator(ArrayList<Type> o0)
    {
        return o0.iterator();
    }

    /** specifies the object composed of the two
     *  cursor objects o0 and o1
     *  (here only o1 is used)
     */ 
    @Override
    public Type composeItems(ArrayList<Type> o0, Type o1)
    {
        return o1;
    }

}

Anwendung

Die folgende Main-Funktion in der Klasse TestNestedArrayList testet den Compound-Iterator für NestedArrayList.

public class TestNestedArrayList
{
    public static void main(String[] args)
    {
        ArrayList<ArrayList<String>> a0;
        ArrayList<String> a1;

        a0=new ArrayList<ArrayList<String>>();

        a1=new ArrayList<String>();   
        a1.add("00");
        a1.add("01");
        a1.add("02");
        a0.add(a1);

        a1=new ArrayList<String>();   
        a1.add("10");
        a0.add(a1);
   
        a1=new ArrayList<String>();   
        a1.add("20");
        a1.add("21");
        a0.add(a1);

        // with compound iterator
        Iterator<String> ci=new NestedArrayList<String>(a0).iterator();
        while (ci.hasNext())
            System.out.print(ci.next()+" ");

        System.out.println();   
    }

}

Zusammenfassung

Die konkret benötigte Funktionalität eines Compound-Iterators wird in einem Behavior (hier NestedArrayList) festgelegt. Dies geschieht durch Angabe eines Basis­iterators, eines Subiterators und der Funktion composeItems.

Zugrunde­gelegt werden dabei getestete Implementierungen der Klassen Compound-Iterator und Compound-IteratorBehavior. Diese finden sich auch im Java-Archiv de.fh-flensburg.inf.lang.iterators.jar.

Für das angegebene sehr einfache Beispiel lohnt sich der Aufwand, einen Compound-Iterator zu benutzen, vielleicht nicht. Dadurch aber, dass der Compound-Iterator selbst das Iterator-Interface implementiert, kann er überall eingesetzt werden, wo ein Iterator stehen kann, also z.B. als Basis­iterator in einem Filter­iterator oder als Subiterator in einem anderen Compound-Iterator.

 

Weiter mit:   [Implementierung CompoundIterator] up

 

homeH.W. Lang   Hochschule Flensburg   lang@hs-flensburg.de   Impressum   ©   Created: 05.02.2008   Updated: 03.03.2017
Valid HTML 4.01 Transitional

Hochschule Flensburg
Campus Flensburg

Informatik in Flensburg studieren...

 

Neu gestaltetes Studienangebot:

Bachelor-Studiengang
Angewandte Informatik

mit Schwerpunkten auf den Themen Software, Web, Mobile, Security und Usability.

Ihr Abschluss
nach 7 Semestern:
Bachelor of Science

 

Ebenfalls ganz neu:

Master-Studiengang
Angewandte Informatik

Ein projektorientiertes Studium auf höchstem Niveau mit den Schwerpunkten Internet-Sicherheit, Mobile Computing und Human-Computer Interaction.

Ihr Abschluss
nach 3 Semestern:
Master of Science

 

Weitere Informatik-Studienangebote an der Hochschule Flensburg:

Medieninformatik

Wirtschaftsinformatik