2017-09-06 1 views
-3

Ich habe ein wenig gegoogelt, war aber nicht in der Lage, eine Lösung für dieses ein bestimmtes Problem zu finden. Ich habe eine List POJOs, die ein Feld (String-Typ) haben. Die displayCode kann verschiedene Formate haben. Einige Beispiele:Vergleichen partiell-numerische Zeichenfolge ohne Casting

622 
622-S 
622-1 
623 
624 
625 
625-S 
625-1 
625-1-S 
625-2 
625-2-S 

Nach der Sortierung sollten sie auch in der Reihenfolge wie oben gezeigt sein. Bei einem normalen s1.compareTo(s2); bekomme ich einen Auftrag wie folgt aus:

1 
10 
100 
101 
102 
... 

die offensichtlich Hotel nicht, was ich brauche. Leider habe ich keine Pläne, wie ich das auf eine glatte Art und Weise erreichen könnte (und auch nicht anders). Bitte beachten Sie auch, dass ich nicht (mit ihm spielen, um Sie können) alles von Java 8.

-Code für Testzwecke verwenden können:

List<String> s = new ArrayList<String>(Arrays.asList(new String[] { "622", "622-S", "622-1", "623", "625", 
     "625-S", "625-1", "625-1-S", "625-2", "625-2-S", "6", "60", "666", "1", "2", "3" })); 
Collections.sort(s,new Comparator<String>() { 

    @Override 
    public int compare(String o1, String o2) { 

     return 0; 
    } 
}); 
System.out.println(s); 

EDIT: Mein erster Gedanke würde werfen die Nummer bis zum ersten zu einem int und vergleiche das und arbeite mich auch zu den anderen Teilen. Das klingt jedoch nicht glatt.

+0

Vielleicht möchten Sie sich auf das konzentrieren, was * funktioniert *, bevor Sie sich um * smooth * kümmern. –

+0

Ihr einziges Problem scheint das S am Ende zu sein, denn normaler Vergleich wird Ihnen geben: 1, 2, 3, 6, 60, 622, 622-1, 622-S, 623, 625, 625-1, 625 -1-S, 625-2, 625-2-S, 625-S, 666 –

+0

Können Sie eine "schlechte" Sortierung für die Elemente in dem Array anzeigen, das Sie oben aufgeführt haben? –

Antwort

1

Es gibt nichts anderes, als den numerischen Teil jeder Zeichenkette zu isolieren, in eine Zahl zu konvertieren, diese zu vergleichen und nur dann, wenn sie gleich sind, den lexikographischen Vergleich der Zeichenketten durchzuführen.

Z. B. entlang dieser Linien (konzeptionellen, wird wahrscheinlich Zwicken müssen):

@Override 
public int compare(String o1, String o2) { 
    String[] p1 = o1.split(" ", 2); 
    String[] p2 = o2.split(" ", 2); 
    try { 
     int n1 = Integer.parseInt(p1[0]); 
     int n2 = Integer.parseInt(p2[0]); 
     if (n1 != n2) { 
      return n1 - n2; 
     } 
     boolean s1 = p1.length > 1 && p1.equals("S"); 
     boolean s2 = p2.length > 1 && p2.equals("S"); 
     if (s1 && !s2) { 
      return -1; 
     } 
     if (!s1 && s2) { 
      return 1; 
     } 
    } catch (NumberFormatException e) { 
    } 
    return o1.compareTo(o2); 
} 
+0

klingt wie die Art, wie ich gehen muss dann – XtremeBaumer

+1

Betrachten Sie die POJO Konstruktor/Setter Splitting 'displayCode' in numerische und string Teile als separate Felder zu halten. Dies würde die Vergleichsmethode vereinfachen, und wenn die "Liste" groß ist, kann das Sortieren möglicherweise schneller gemacht werden. –

0

Java-Strings haben eine split Methode, die Sie den numerischen Teil Ihres POJOs verwenden können, zu isolieren; dann können Sie parseInt verwenden, um das POJO als eine ganze Zahl zu erhalten, die das Sortieren so machen würde, wie Sie es wünschen.

1

Dies könnte Ihnen helfen.

Collections.sort(s, new Comparator<String>() { 

      public int compare(String o1, String o2) { 
       int returnValue = -1; 

       Integer left = returnIfNumeric(o1); 
       Integer right = returnIfNumeric(o2); 

       // if both values are number 
       if (left != null && right != null) { 
        if (left > right) 
         returnValue = 1; 
        else if (left == right) 
         returnValue = 0; 
        else 
         returnValue = -1; 
       } 
       // if both values are string 
       else if (left == null && left == right) { 
        return o1.compareTo(o2); 
       } 
       // if left is number 
       else if (left != null) { 
        returnValue = -1; 
       } 
       // if left is string 
       else { 
        returnValue = 1; 
       } 

       return returnValue; 
      } 
     }); 

    } 

    public static Integer returnIfNumeric(String str) { 
     Integer number = null; 
     try { 
      number = Integer.valueOf(str); 
     } catch (NumberFormatException nfe) { 
      number = null; 
     } 
     return number; 
    } 
Verwandte Themen