Коллекции Treemap и TreeSet Не могу дописать компаратор
Задача реализовать компаратор, сортировка которым расставит кандидатов по убыванию их приоритета найма в астронавты. Ничего кроме класса компаратора менять нельзя.
Программа в main в итоге должна выводить имена двух самых лучших кандидатов
- тот у кого больше опыта;
- если опыт одинаковый то тот, у кого в имени с фамилией (т.е. name) больше букв s или S (от слова space - космос; было решено, что медийность - важная часть космонавтики);
- если по этому критерию оказываются равны, то тот, у кого имя с фамилией (т.е. name) короче (так легче будет запоминать имена астронавтов по всему миру)
import java.util.Comparator;
import java.util.Iterator;
import java.util.TreeSet;
public class Main {
public static void main(String[] args) {
TreeSet<Person> candidates = new TreeSet<>(new SpacePersonComparator());
candidates.add(new Person("Sonya Popova", 35, 15));
candidates.add(new Person("Dazdraperma Sponzhova", 33, 15));
candidates.add(new Person("Salavat Netologshvili", 23, 13));
candidates.add(new Person("Sasha Sun", 31, 15));
candidates.add(new Person("Svetlana Morkov", 38, 15));
candidates.add(new Person("Sasha Sosnova", 38, 11));
Iterator<Person> it = candidates.iterator();
System.out.println(it.next());
System.out.println(it.next());
}
}
class Person {
private String name;
private int age;
private int experience;
public Person(String name, int age, int experience) {
this.name = name;
this.age = age;
this.experience = experience;
}
public String getName() {
return name;
}
public int getAge() {
return age;
}
public int getExperience() {
return experience;
}
@Override
public String toString() {
return name;
}
}
class SpacePersonComparator implements ... { // укажите интерфейс
// имплементируйте его
}
Ответы (1 шт):
Компаратор SpacePersonComparator должен реализовать интерфейс Comparator<Person>, то есть, в нём следует переопределить метод Comparator::compare.
При этом сравнение по опыту работы (experience) и количеству букв 'S' должно выполняться в обратном порядке (чтобы люди были отсортированы по убыванию).
Вариант реализации в классическом стиле до Java 8:
class SpacePersonComparator implements Comparator<Person> {
@Override
public int compare(Person p1, Person p2) {
int res = Integer.compare(p2.getExperience(), p1.getExperience()); // по убыванию опыта
if (res == 0) {
res = Integer.compare(countS(p2.getName()), countS(p1.getName())); // по убыванию количества 'S'
}
if (res == 0) {
res = Integer.compare(p1.getName().length(), p2.getName().length()); // по возрастанию длины имени
}
return res;
}
private static int countS(String name) {
return name.replaceAll("[^Ss]", "").length();
}
}
Результат теста:
Sasha Sun
Sonya Popova
Начиная с Java 8, в котором появились функциональные интерфейсы, лямбда-выражения, ссылки на методы, реализация компараторов в отдельном классе уже не является необходимой, и они могут определяться в "декларативном" стиле:
Comparator<Person> spacePersonComparator = Comparator.
comparing(Person::getExperience, Comparator.reverseOrder())
.thenComparing(p -> countS(p.getName()), Comparator.reverseOrder())
.thenComparingInt(p -> p.getName().length());
TreeSet<Person> candidates = new TreeSet<>(spacePersonComparator);
// ...