Каков тип Map.Entry.comparingByValue(). Reversed()?

У меня есть список записей на карте

Map<String, Integer> map = new HashMap<>();
...(fill the map)...
List<Entry<String, Integer>> entries = new ArrayList<>(map.entrySet());

и я хочу отсортировать его по значениям в соответствии с этим ответом, но в обратном порядке. Когда я делаю

Comparator<Entry<String, Integer>> cmp = Entry.comparingByValue();
entries.sort(cmp.reversed());

все отлично работает Но когда я пытаюсь сократить вышеупомянутые две строки,

entries.sort(Entry.comparingByValue().reversed());

компилятор возвращает

error: incompatible types: Comparator<Entry<Object,V>> cannot be converted to Comparator<? super Entry<String,Integer>>
        entries.sort(Entry.comparingByValue().reversed());
  where V is a type-variable:
    V extends Comparable<? super V>

Это кажется странным, потому что реализация Comparator's reversed() метод по умолчанию просто передает его Collections.reverseOrder() и я могу изменить вышеуказанную строку на

entries.sort(Collections.reverseOrder(Entry.comparingByValue()));

работать. Но каков правильный тип Entry.comparingByValue().reversed()?

Comparator<Entry<String, Integer>> cmp = Entry.comparingByValue().reversed();

не похоже на работу. Пропуск параметра типа Entry<String, Integer> работает, но это приводит к предупреждению "непроверенный вызов метода" от компилятора позже.

2 ответа

Решение

Компилятор не достаточно умен, чтобы выводить параметры универсального типа в этом случае. Вы можете указать их явно:

entries.sort(Entry.<String, Integer>comparingByValue().reversed());

Проблема в том, что вам сначала нужен тип компаратора, возвращаемый comparingByValue знать тип возвращаемого reversed,

Я не вижу веской причины, почему умный компилятор не мог работать задом наперед и знать, что sort требует определенного типа, поэтому reversed должен быть определенного типа, так comparingByValue должен быть определенного типа. Но это не так.

Вывод типа все еще работает ( совсем недавно, как Java 10), так что, возможно, в будущем, кто знает.

Когда вы сокращаете

Comparator<Entry<String, Integer>> cmp = Entry.comparingByValue();
entries.sort(cmp.reversed());

в

entries.sort(Entry.comparingByValue().reversed());

Вы удаляете информацию о типе, почерпнутую из cmpдекларация Компилятор все еще должен знать эту информацию, поэтому вам нужно добавить общий тип Entry:

entries.sort(Entry.<String, Integer>comparingByValue().reversed());
Другие вопросы по тегам