Frage zum Sortieren einer Liste

Cherry07

Mitglied
Hallo,

ich sollte eine PlayListe die von LinkedList abgeleitet ist nach 4 Kriterien sortieren und möchte euch mal fragen, ob das so stimmt wie ich es gemacht habe.
Bei dieser Aufgabe gibt es eine Klasse Enum SortierKriterium, eine Klasse PlayListe und eine Klasse AudioFile, die noch weitere Subklassen besitzt.
Ich beschränke mich hier nur auf die relevanten Klassen bzw. CodeAusschnitte, da das ganze Projekt viel zu umfangreich ist.

Hier erstmal die Klasse Enum SortierKriterium:
Code:
public enum SortierKriterium
{
        AUTOR, TITEL;     //SortierKriterien

        private static SortierKriterium sortKrit;

        SortCriterion ()
        {     
        }
        //statische Getter und Setter für das Attribut
}

dann die Klasse AudioFile, die das Interface Comparable implementiert und nur AudioFile-Objekte vergleichen soll:
(in dieser Klasse wird bzgl. der Sortierung nur die Methode compareTo von Comparable implementiert...)
Code:
abstract class AudioFile
implements Comparable<AudioFile> 
//hier findet nur die Extrahierung von Autor und Titel innerhalb eines Pfadnamens ab und 
//ein paar abstract Methoden wie play(), usw. (was im Grunde unwichtig für die Sortierung 
//ist

public int compareTo(AudioFile other)
{ 
        //AudioFile.compareTo gibt den Wert des Vergleichs des eigenen Titels mit dem des 
        //anderen AudioFiles zurück, wenn sortKrit == TITEL ist
        if (SortierKriterium.getSortKrit() == SortierKriterium.TITEL)
            return this.titel.compareTo(other.getTitle());
         
        //analog dazu dann auch mit AUTOR
        else if (SortierKriterium.getSortKrit() == SortierKriterium.AUTOR)
            return this.autor.compareTo(other.getAutor());
        
        else
            return 0;
}

und zu allerletzt die PlayListe, die von LinkedList abgeleitet ist:
Code:
import java.util.LinkedList;
import java.util.Collections;

public class PlayList 
extends LinkedList<AudioFile>
{
    //...
    //die sort-Methode bekommt ein Sortkriterium übergeben und belegt damit sortKrit vor
    public void sort(SortierKriterium sortKrit)
    {
        SortierKriterium.setSortKrit (sortKrit);
        Collections.sort(this);
    }
    //...
    //
     public static void main (String[] args)
     {   
        PlayList pl1 = new PlayList();
        //in pl1 wird dann einpaar Pfade eingefügt, wo sich halt der Song befindet
        //dann wird mit pl1.sort aufgerufen
        pl1.sort(SortierKriterium.AUTOR);
     }
}


Vielen Dank erstmal und ein schönes Wochende
cherry07
 
Also mit was statischem sollte man nur sehr sparsam arbeite und das ist hier absolut nicht angebracht sondern zeigt nur mangelnde Objektorientierte Programmierung. Du könntest so ja nicht gleichzeitig nach zwei Sachen sortieren. Static ist selten angebracht, versuche das zu vermeiden (es sei denn für Konstanten static final)

Eigentlich sollte doch dass Sortierkriterium wissen wie zu sortieren ist oder? So würde ich es von dem Objekt erwarten. Nun man kann Enums auch Methoden geben:

Java:
import java.util.Collections;
import java.util.Comparator;

public enum SortierKriterium {
	AUTOR {
		public Comparator<AudioFile> getComparator() {
			Comparator<AudioFile> comp = new Comparator<AudioFile>() {

				@Override
				public int compare(AudioFile o1, AudioFile o2) {
					return o1.getTitle().compareTo(o2.getTitle());
				}

			};
			return comp;
		}
	}

	,
	TITEL {
		public Comparator<AudioFile> getComparator() {
			Comparator<AudioFile> comp = new Comparator<AudioFile>() {

				@Override
				public int compare(AudioFile o1, AudioFile o2) {
					return o1.getAutor().compareTo(o2.getAutor());
				}

			};
			return comp;
		}
	};

	public abstract Comparator<AudioFile> getComparator();

}

Aufruf:
Java:
public void sort(SortierKriterium sortKrit)
    {
        Collections.sort(this,sortKrit.getComparator());
    }

Schicker oder?
 
Hallo,

erstmals danke für deine Hilfe.
Ich find auch des deine Lösung viel besser ist als meine. Aber lt. Aufgabenstellung sollte das Attribut schon static sein.
Ja schon die eigentliche Sortierung nimmt die API vor, da hast du recht, aber lt. Aufgabenstellung sollte das Sortieren nach mehren Kriterien möglich sein.

"SortierKriterium bekommt ein statisches Attribut sortKrit, das das momentane Sortierkriterium angibt. Dieses Attribut hat einen statischen getter und setter.
Die sort-Methode von PlayList bekommt als Parameter ein Sortierkriterium übergeben und belegt diese vor, bevor es Collections.sort(this) aufruft.
AudioFile und deren Subklassen bekommen eine compareTo-Methode, die in Abhängigkeit vom Attribut sortKrit einen Vergleich vornimmt."
So war leider die Aufgabenstellung.

Aber wenn ich es so wie du mache, dann kann ich doch nicht public static SortKriterium sortkrit; in enum SortierKriterium machen, oder.

Schönes Wochenende
cherry07
 
Wer bitte stellt denn so eine Aufgabe? Ich würde mich weigern das so zu lösen weil das absoluter Unsinn ist.

Dann machs halt so wie dus vorher hattest. Und schreib bei der Lösung drunter wie mans eigentlich ordentlich macht....
 
Ich trau mich ehrlich gesagt auch nicht, danach zu fragen, wer so eine Aufgabe stellt. Das zeugt einzig und allein davon, dass jemand wenig Ahnung von OO hat. Deine Klasse wird daurch inherent threadunsafe (sorry, Zeja ;)). Zumal es in diesem Fall absolut keinen Grund gibt, das Ding static zu machen.

Zejas Lösung ist zum einen eleganter und zum anderen wesentlich objektorientierter ;).

Gruß
Ollie
 
Hallo,

ich hab ein ähnliches Problem wie der Threadersteller. Die Aufgabenstellung ist bei mir jedoch etwas anders.
Ich muss für jedes der 4 Sortierkriterien eine eigene Comparatorklasse erstellen. Laut JUnit-Test funktioniert die Sortierung jedoch nicht. Was mache ich hier falsch?
Vielen Dank im Voraus.


Code der Sortierung:

Code:
public class PlayList extends LinkedList<AudioFile> {
...

public void sort (SortCriterion order){
        if (order.contains(SortCriterion.AUTHOR))
            Collections.sort(this, new AuthorComparator());
        if (order.contains(SortCriterion.TITLE)) 
            Collections.sort(this, new TitleComparator());
        if (order.contains(SortCriterion.ALBUM)) 
            Collections.sort(this, new AlbumComparator());
        if (order.contains(SortCriterion.DURATION))
            Collections.sort(this, new DurationComparator());
    }
...
}

Beispielhaft hier die Comparatorklasse für AUTHOR:

Code:
 public class AuthorComparator implements Comparator<AudioFile> {
    
// der Getter getAuthor() bezieht sich auf eine weitere Klasse (AudioFile) in der der Fehler allerdings nicht liegen dürfte

    public AuthorComparator() {
        // TODO Auto-generated constructor stub  
        }

    public int compare (AudioFile af1, AudioFile af2) {
        
        return (af1.getAuthor().compareTo(af2.getAuthor()));
        }



Code:
 public enum SortCriterion {
    AUTHOR, TITLE, ALBUM, DURATION;

    public boolean contains(SortCriterion author2) {
        // TODO Auto-generated method stub
        return false;     }
 
Hallo,

naja, ich könnte mir vorstellen, dass deine contains-Methode im SuchKriterium der Grund ist.
Da sie immer false zurück gibt, ist die Wahrscheinlichkeit, dass irgendeine if-Anweisung ausgeführt wird gleich null. ;-)

Gruß

Sascha
 
Die contains-Methode wurde ja von Eclipse so angelegt und verlangt ausdrücklich einen Rückgabewert. Was sollte ich da stattdessen zurückgeben?
 
Naja, ich schätze du wolltest vergleichen, ob es sich um ein bestimmtes Kriterium handelt.
Da weiß ich jetzt ehrlich gesagt nicht was du mit dieser Methode möchtest.

Code:
order == SortCriterion.AUTHOR

sollte schon eher passen.

Gruß

Sascha
 

Neue Beiträge

Zurück