# EJB --- Sortierung



## bronks (22. Mai 2006)

Hi!

Wieder das bekannte Datenmodell:




Ich hole mir aus der ZauftragBean einen Auftrag. Mit getZauftragpositionBean() hole ich mir aus dem Auftrag eine Collection mit den Auftragspositionen. 

Die Auftragspositionen erhalte ich nicht immer nach der Positionsnummer sortiert und es könnte auch vorkommen, daß ich diese ganz anders sortiert haben möchte.

Wo muß ich für die Sortierung sorgen bzw. wie bekomme ich das am besten sortiert?

Danke

Bronks


----------



## Guest (22. Mai 2006)

Siehe
	
	
	
	





```
Collections.sort(List<T> list, Comparator<? super T> c)
```
Wenn es nicht überall sortiert sein muss, dann nur dort sortieren, wo es nötig ist,
ansonsten bereits serverseitig in der betreffenden Business- bzw. Facademethode.


----------



## bronks (23. Mai 2006)

Anonymous hat gesagt.:
			
		

> Siehe
> 
> 
> 
> ...


Danke, aber kennst Du zufällig ein gutes Beispiel dafür, wie man damit korrekt umgeht?

bzw. wie muß ich es für dieses Beispiel anwenden, um die ArrayList nach Nachnamen sortiert zu bekommen:



```
ArrayList list = new ArrayList();
        
        //PersonDTO beinhaltet Vorname und Nachname
        list.add(new PersonDTO("Peter","Müller"));
        list.add(new PersonDTO("Daniel","Schmidt"));
        list.add(new PersonDTO("Hans","Glatt"));
        list.add(new PersonDTO("Peter","Maier"));
        list.add(new PersonDTO("Beatrix","Müller"));
```


----------



## KSG9|sebastian (23. Mai 2006)

```
final Comparator cmp = new Comparator(){
   public int compare(Object o1,
                   Object o2){
        //prüfen ob die zu vergleichenden Objekte nicht null sind und vom Typ ein PersonDTO sind
       if(o1 != null && 
          o2 != null && 
          o1 instanceof PersonDTO &&    
          o2 instanceof PersonDTO){
                 return ((PersonDTO)o1).getNachname().compareTo(((PersonDTO)o2).getNachname());
       }
       return 0;
   }
};

ArrayList list = new ArrayList(); 
        
        //PersonDTO beinhaltet Vorname und Nachname 
        list.add(new PersonDTO("Peter","Müller")); 
        list.add(new PersonDTO("Daniel","Schmidt")); 
        list.add(new PersonDTO("Hans","Glatt")); 
        list.add(new PersonDTO("Peter","Maier")); 
        list.add(new PersonDTO("Beatrix","Müller"));

Collections.sort(list, cmp);
```

Edit:

Ach ja, Werte bei compare:

Rückgabe | Ergebnis

<0           |  o1 < o2
=0           |  o1 = o2
>0           |  o1 > o2


----------



## KSG9|sebastian (23. Mai 2006)

Andere Möglichkeit ist dass deine PersonDTO-Klasse das Interface Comparable implementiert. Die Methode sieht gleich aus wie die des Comparators.

Dann reicht der Aufruf Collection.sort(list);


----------



## Guest (23. Mai 2006)

Ich würde mal davon ausgehen, dass der Comparator für List mir PersonDTO-Objekten gedacht ist
und dass Vor- und Nachname nicht null sind.
Ausserdem kann man sich die Typenprüfung und null-Werte innerhalb der Liste sparen, da ArrayList 
keine null-Werte enthalten kann.
	
	
	
	





```
final Comparator cmp = new Comparator() { 

  public int compare(Object o1, Object o2) { 
    PersonDTO p1 = (PersonDTO)o1; // Bei falscher Anwendung des Comparators ClassCastException (=Programmierfehler)
    PersonDTO p2 = (PersonDTO)o2;
    
    boolean result = p1.getNachname().compareTo(p2.getNachname());
    
    // Wenn Nachnamen gleich, dann innerhalb der Nachnamen nach Vornamen sortieren
    if(result==0) {
      result = p1.getVorname().compareTo(p2.getVorname());
      
      // Wenn Vornamen ebenfalls gleich, dann nach sonstwas sortieren ;-)
      if(result==0) {
        result = ...
      }
    }
     
    return result; 
  } 

};

// oder in JDK 1.5.x ohne die Casts (dies setzt aber vcoraus, dass du List<PersonDTO> verwendest)
final Comparator<PersonDTO> cmp = new Comparator<PersonDTO>() { 

  public int compare(PersonDTO p1, PersonDTO p2) { 
    boolean result = p1.getNachname().compareTo(p2.getNachname());

    // Wenn Nachnamen gleich, dann innerhalb der Nachnamen nach Vornamen sortieren
    if(result==0) {
      result = p1.getVorname().compareTo(p2.getVorname());
      
      // Wenn Vornamen ebenfalls gleich, dann nach sonstwas sortieren ;-)
      if(result==0) {
        result = ...
      }
    }
     
    return result; 
  }
 
};
```


----------



## KSG9|sebastian (24. Mai 2006)

Also diverse Kontrollstrukturen kann man ja weglassen, aber dein Code ergibt keinen Sinn :

compareTo gibt ein int zurück und du speicherst es als boolean.
dannach behandelst du es wieder als int 


```
final Comparator cmp = new Comparator(){ 
   public int compare(Object o1, 
                   Object o2){ 

                int res = ((PersonDTO)o1).getNachname().compareTo(((PersonDTO)o2).getNachname()); 
               return res == 0?((PersonDTO)o1).getVorname().compareTo(((PersonDTO)o2).getVorname()) : res;

   } 
};
```


----------



## Guest (25. Mai 2006)

Stimmt, mach aus dem boolean ein int, dann ist es wieder OK.


----------

