Java: сортировать хэш-карту по ключам и значениям

Я хочу отсортировать хеш-карту по ключам и значениям. В настоящее время я отсортировал карту по значениям, но ключ содержит строку, которую я хочу отсортировать, не нарушая ранее отсортированную карту по значениям?

карта после сортировки по значениям

{Login to new=27, Failed login=27, Impossible=21}

Как я хочу отсортировать карту

{Failed login =27, Login to new =27, Impossible =21}

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

P.S Я новичок в java

изменить: добавление функции сортировки, которую я взял из переполнения стека

    public static <K, V extends Comparable<? super V>> Map<K, V
    sortByValue(Map<K, V> map) {
    List<Map.Entry<K, V>> list = new LinkedList<>(map.entrySet());
    Collections.sort(list, new Comparator<Map.Entry<K, V>>() {
        @Override
        public int compare(Map.Entry<K, V> e1, Map.Entry<K, V> e2) {
            return (e2.getValue()).compareTo(e1.getValue());
        }
    });
    Map<K, V> result = new LinkedHashMap<>();
    for (Map.Entry<K, V> entry : list) {
        result.put(entry.getKey(), entry.getValue());
    }
    return result;
}

Покажите нам свой код, чтобы мы могли помочь вам выявить проблемы.

BluesSolo 31.10.2018 11:35

так что в основном конечным результатом должна быть карта с отсортированными ключами и значениями, верно?

Amit Kumar Lal 31.10.2018 11:39

@Hades Да! он должен быть на карте.

jaisimha kulkarni 31.10.2018 11:44

@jaisimhakulkarni Я реализовал решение с использованием TreeMap без дополнительной итерации, дайте мне знать, работает ли оно

Amit Kumar Lal 01.11.2018 05:44
0
4
816
4
Перейти к ответу Данный вопрос помечен как решенный

Ответы 4

Ответ принят как подходящий

вы можете написать свой собственный компаратор, как показано ниже -

class MapValueKeyComparator<K extends Comparable<? super K>, V extends Comparable<? super V>>
        implements Comparator<Map.Entry<K, V>> {

    public int compare(Map.Entry<K, V> a, Map.Entry<K, V> b) {
        int cmp1 = b.getValue().compareTo(a.getValue()); //can reverse a and b position for ascending/descending ordering
        if (cmp1 != 0) {
            return cmp1;
        } else {
            return a.getKey().compareTo(b.getKey()); //can reverse a and b position for ascending/descending ordering
        }
    }

}

Поместите все записи карты в список и отсортируйте их -

  HashMap<String, Integer> map = new HashMap<String, Integer> ();

    map.put("Login to new", 27);
    map.put("Failed login", 27);
    map.put("Impossible", 21);

  List<Map.Entry<String, Integer>> list = new ArrayList<Map.Entry<String, Integer>>(map.entrySet());
   Collections.sort(list, new MapValueKeyComparator<String, Integer>());

  for(Map.Entry<String, Integer> m : list){
     System.out.println(m);
  }

Выход -

Неудачный вход = 27 Войти в new = 27 Невозможно = 21

Объяснение - MapValueKeyComparator сортирует ключ и значение заданной карты, где сначала сортируются значения, а затем ключи. В основном коде помещаются все записи карты в список, чтобы его можно было отсортировать с помощью этого компаратора, используя класс java Collections util.

Спасибо большое, сэр!. Это действительно работает, как ожидалось. Также не могли бы вы уточнить, что происходит в вашем коде?

jaisimha kulkarni 31.10.2018 12:37

Вы можете сортировать содержимое карты так, как вы описываете; однако на выходе будет список, то есть отсортированный список. Затем вам нужно будет обработать список, чтобы получить желаемый результат.

Этот код должен делать то, что вы хотите:

    Comparator<Entry<String, Integer>> byKeyThenByValue = Comparator.comparing(
            entry -> entry.getKey() + entry.getValue());

    List<Entry<String, Integer>> outList = mymap.entrySet().stream()
            .peek(entry -> System.out.println("K: " + entry.getKey() + "  v: " + entry.getValue()))
            .sorted(byKeyThenByValue)
            .collect(Collectors.toList());
    System.out.println(outList);

    Map<Object, Object> outMap = new LinkedHashMap<>();
    outList.forEach(entry -> outMap.put(entry.getKey(), entry.getValue()));
    System.out.println(outMap);

Сделайте что-нибудь вроде этого

Первая сортировка по ключам и после сортировки по значениям

    Map<String, Integer> map=new HashMap<String, Integer>();
     map.put("Login to new", 27);
     map.put("Failed login", 27);
     map.put("Impossible", 21);

     List<Map.Entry<String, Integer>> list = new LinkedList<Map.Entry<String, Integer>>(map.entrySet());

        //sort keys in ascending order
        Collections.sort(list, new Comparator<Map.Entry<String, Integer>>() {
            @Override
            public int compare(Map.Entry<String, Integer> e1, Map.Entry<String, Integer> e2) {
                return (e1.getKey()).compareTo(e2.getKey());
            }
        });

        //sort by values in descending order
        Collections.sort(list, new Comparator<Map.Entry<String, Integer>>() {
            @Override
            public int compare(Map.Entry<String, Integer> e1, Map.Entry<String, Integer> e2) {
                return (e2.getValue()).compareTo(e1.getValue());
            }
        });


        Map<String, Integer> result = new LinkedHashMap<String, Integer>();
        for (Map.Entry<String, Integer> entry : list) {
            result.put(entry.getKey(), entry.getValue());
        }
        System.out.println(result);

Выход

{Failed login=27, Login to new=27, Impossible=21}
public static void main(String...strings) throws IOException {
        Map<String, String[]> map = new TreeMap<String, String[]>(){            
            @Override
            public String[] put(String key, String[] value){
                Arrays.sort(value);
                return super.put(key, value);
            }
        };

        map.put("Apple11", new String[]{"Zinc", "Iridium", "Apple"});
        map.put("Apple1", new String[]{"Xenon", "Zinc", "Brass"});

        for (Entry<String, String[]> entry : map.entrySet()) {
            System.out.println(entry.getKey()+"  ::  "+Arrays.toString(entry.getValue()));
        }
    }

выход ::

Apple1  ::  [Brass, Xenon, Zinc]
Apple11  ::  [Apple, Iridium, Zinc]

Другие вопросы по теме