2013-03-04 5 views
0

Я хотел бы отсортировать массив объектов. Каждый объект имеет метод getType(), который возвращает тип объекта в String.Компаратор для групп типов

Я хотел бы отсортировать мой массив в зависимости от типа с чем-то вроде приоритетов.

Пример:

Input { A, F, Z, G, E, D, C } 

If(type == A or B or C or D) top 
If(type == E) second 
If(type == F or G) third 
If(differet type) last 

Output: { A, C, D, E, F, G, Z } 

Как должен мой компаратор выглядеть?

Если я не изложил свой вопрос достаточно ясно, напишите комментарий, я попытаюсь более кратко объяснить часть, которая не ясна.

+0

является 'type' строкового значения –

+3

Почему ваш выход начинается {A, C, D}? Неужели так же легко быть {D, A, C}? т. е. все элементы в ваших группах эффективно равны? Что вы пробовали? –

+1

Все ли ваши объекты одного класса или они по крайней мере наследуются от одного и того же интерфейса/класса? Или они все разные классы (каждый тип, представляющий другой класс)? – Dukeling

ответ

3

Вы можете объявить приоритетов по хэш-карта:

private static final HashMap<String,Integer> PRIORITIES = new HashMap<String, Integer>(); 
static{ 
    PRIORITIES.put("A", 1); 
    PRIORITIES.put("B", 1); 
    PRIORITIES.put("C", 1); 
    PRIORITIES.put("D", 1); 
    PRIORITIES.put("E", 2); 
    PRIORITIES.put("F", 2); 
    PRIORITIES.put("G", 3); 
} 

Затем реализовать compare метод вашего Comparator:

private int getPriority(CustomClass obj) { 
    if(obj!=null&&PRIORITIES.containsKey(obj.getType())) { 
     priority1 = PRIORITIES.get(obj.getType()); 
    } else { 
     priority1 = Integer.MAX_VALUE; 
    } 
} 

@Override 
public int compare(CustomClass o1, CustomClass o2) { 
    int priority1,priority2; 
    priority1 = getPriority(o1); 
    priority2 = getPriority(o2); 
    return priority1==priority2 ? 0 : (priority1<priority2 ? -1 : 1); 
} 

UPDATE: уборщик подход заключается в определении HashMap в вашем базовом классе (где getType) и для осуществления getPriority:

public int getPriority() { 
    return PRIORITIES.containsKey(getType()) ? PRIORITIES.get(getType()) : Integer.MAX_VALUE; 
} 

Тогда Comparator очевидна:

@Override 
public int compare(CustomClass o1, CustomClass o2) { 
    int priority1,priority2; 
    priority1 = o1==null ? Integer.MAX_VALUE : o1.getPriority(); 
    priority2 = o2==null ? Integer.MAX_VALUE : o2.getPriority(); 
    return priority1==priority2 ? 0 : (priority1<priority2 ? -1 : 1); 
} 
+1

Я нашел, ваш ответ наиболее полезен. Благодарим вас за то, что вы смотрите на мой ответ и делитесь своими знаниями! – Datenshi

+0

@ Datenshi Спасибо! Удачи! –

1

Пусть ваши объекты Comparable<ElementType> интерфейс (так как все они одного и того же класса (позволяет сказать ElementType и вызов Arrays.sort(myArray). Если вы хотите, чтобы отсортировать объект, используя разные иной порядок каждый раз, то вы должны создать объект Comparator

Вы можете увидеть хорошие примеры here

2

я бы, вероятно, сделать что-то вроде этого:

class Comparer implements Comparator<YourType> 
{ 
    @Override 
    public int compare(YourType o1, YourType o2) 
    { 
     return Integer.compare(getRank(o1), getRank(o2)); 
     // Pre-Java 7 
     //Integer v1 = getRank(o1); 
     //return v1.compareTo(getRank(o2)); 
    } 

    int getRank(YourType o) 
    { 
     switch (o.getType()) 
     { 
     case "A": case "B": case "C": case "D": 
      return 1; 
     case "E": 
      return 2; 
     case "F": case "G": 
      return 3; 
     default: 
      return 4; 
     } 
    } 
} 

Тогда:

YourType[] arr = ...; 
Arrays.sort(arr, new Comparer()); 

выше будет работать только в Java 7 и выше, потому что switch на String не поддерживается до Java 7.

Если вы не используете Java 7, вам нужно будет использовать if-statements вместо switch.

+0

Ваш ответ верный, но я думаю, что по умолчанию locale aproach лучше, поэтому я приму его ответ. Но спасибо за ваше время и полезный ответ :-) – Datenshi

0

Вы также можете использовать класс Guava'sOrdering, чтобы отсортировать вход для вас. Если объекты, которые вы имеете дело с есть понятие «естественного» порядка, то вы можете сделать что-то вроде Ordering<Input>.natural или реализовать свой собственный компаратор внутри конкретизации:

Ordering<Input> getInputOrder = new Ordering<Input>() { 
public int compare(Input A, Input B) { 
    return A.comparableMember > B.comparableMember 
} 
}; 
Смежные вопросы