it-swarm.com.de

Wie sortiere ich Kartenwerte nach Schlüssel in Java?

Ich habe eine Map, die Zeichenfolgen für Schlüssel und Werte enthält. 

Daten sind wie folgt: 

"Frage1", "1"
"Frage 9", "1"
"Frage2", "4"
"question5", "2" 

Ich möchte die Karte nach ihren Schlüsseln sortieren. Am Ende werde ich question1, question2, question3.... und so weiter haben. 


Ich versuche, zwei Strings aus dieser Map herauszuholen. 

  • Erster String: Fragen (in der Reihenfolge 1 ..10)
  • Zweiter String: Antworten (in derselben Reihenfolge wie die Frage)

Im Moment habe ich folgendes:

Iterator it = paramMap.entrySet().iterator();
while (it.hasNext()) {
    Map.Entry pairs = (Map.Entry) it.next();
    questionAnswers += pairs.getKey() + ",";
}

Das bringt mir die Fragen in einem String, aber sie sind nicht in Ordnung.

320
n00bstackie

Kurze Antwort

Verwenden Sie eine TreeMap . Genau dafür ist es da. 

Wenn diese Karte an Sie übergeben wird und Sie den Typ nicht bestimmen können, können Sie Folgendes tun:

SortedSet<String> keys = new TreeSet<>(map.keySet());
for (String key : keys) { 
   String value = map.get(key);
   // do something
}

Dadurch wird die Karte in natürlicher Reihenfolge der Schlüssel durchlaufen.


Längere Antwort

Technisch können Sie alles verwenden, was SortedMap implementiert, aber außer in seltenen Fällen beläuft sich diese auf TreeMap, genau wie die Verwendung einer Map-Implementierung HashMap

In Fällen, in denen Ihre Schlüssel ein komplexer Typ sind, der Comparable nicht implementiert oder Sie die natürliche Reihenfolge nicht verwenden möchten, verfügen TreeMap und TreeSet über zusätzliche Konstruktoren, mit denen Sie eine Comparator übergeben können:

// placed inline for the demonstration, but doesn't have to be a lambda expression
Comparator<Foo> comparator = (Foo o1, Foo o2) -> {
        ...
    }

SortedSet<Foo> keys = new TreeSet<>(comparator);
keys.addAll(map.keySet());

Denken Sie bei der Verwendung einer TreeMap oder TreeSet daran, dass sie andere Leistungsmerkmale aufweist als HashMap oder HashSet. Grob gesagt gehen Operationen, die ein Element finden oder einfügen, von O(1) nach O(Log(N)).

In einer HashMap wirkt sich das Wechseln von 1000 Elementen auf 10.000 nicht wirklich auf die Zeit aus, um ein Element zu suchen. Bei einer TreeMap ist die Suchzeit jedoch etwa dreimal langsamer (vorausgesetzt, Log.)2). Der Wechsel von 1000 auf 100.000 ist bei jeder Element-Suche etwa sechsmal langsamer.

562
Jherico

Angenommen, TreeMap ist nicht gut für Sie (und Sie können keine Generics verwenden):

List sortedKeys=new ArrayList(yourMap.keySet());
Collections.sort(sortedKeys);
// Do what you need with sortedKeys.
126
TrayMan

Mit der TreeMap können Sie die Karte sortieren.

Map<String, String> map = new HashMap<>();        
Map<String, String> treeMap = new TreeMap<>(map);
for (String str : treeMap.keySet()) {
    System.out.println(str);
}
48
Manoj Singh

Verwenden Sie eine TreeMap !

34
AgileJon

Wenn Sie bereits über eine Karte verfügen und diese nach Schlüsseln sortieren möchten, verwenden Sie einfach:

Map<String, String> treeMap = new TreeMap<String, String>(yourMap);

Ein vollständiges Arbeitsbeispiel:

import Java.util.HashMap;
import Java.util.Set;
import Java.util.Map;
import Java.util.TreeMap;
import Java.util.Iterator;

class SortOnKey {

public static void main(String[] args) {
   HashMap<String,String> hm = new HashMap<String,String>();
   hm.put("3","three");
   hm.put("1","one");
   hm.put("4","four");
   hm.put("2","two");
   printMap(hm);
   Map<String, String> treeMap = new TreeMap<String, String>(hm);
   printMap(treeMap);
}//main

public static void printMap(Map<String,String> map) {
    Set s = map.entrySet();
    Iterator it = s.iterator();
    while ( it.hasNext() ) {
       Map.Entry entry = (Map.Entry) it.next();
       String key = (String) entry.getKey();
       String value = (String) entry.getValue();
       System.out.println(key + " => " + value);
    }//while
    System.out.println("========================");
}//printMap

}//class
32
M-D

Verwenden Sie einfach TreeMap

new TreeMap<String, String>(unsortMap);

Beachten Sie, dass die TreeMap nach der natürlichen Reihenfolge ihrer 'Schlüssel' sortiert ist.

28
Aliti

Vorausgesetzt, Sie können TreeMap nicht verwenden, können Sie in Java 8 die Methode toMap () in Collectors verwenden, für die folgende Parameter erforderlich sind:

  • keymapper: Zuordnungsfunktion zur Erzeugung von Schlüsseln
  • valuemapper: Zuordnungsfunktion zur Erzeugung von Werten
  • mergeFunction: Eine Merge-Funktion, mit der __. Kollisionen zwischen Werten gelöst werden, die demselben Schlüssel zugeordnet sind
  • mapSupplier: Eine Funktion, die eine neue leere Map zurückgibt, in die die -Ergebnisse eingefügt werden.

Java 8 Beispiel

Map<String,String> sample = new HashMap<>();  // Push some values to map  
Map<String, String> newMapSortedByKey = sample.entrySet().stream()
                    .sorted(Map.Entry.<String,String>comparingByKey().reversed())
                    .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue, (e1, e2) -> e1, LinkedHashMap::new));
Map<String, String> newMapSortedByValue = sample.entrySet().stream()
                        .sorted(Map.Entry.<String,String>comparingByValue().reversed())
                        .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue, (e1,e2) -> e1, LinkedHashMap::new));

Wir können das Beispiel ändern, um einen benutzerdefinierten Vergleicher zu verwenden und nach Schlüsseln zu sortieren:

Map<String, String> newMapSortedByKey = sample.entrySet().stream()
                .sorted((e1,e2) -> e1.getKey().compareTo(e2.getKey()))
                .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue, (e1,e2) -> e1, LinkedHashMap::new));
12
i_am_zero

Java 8 verwenden:

Map<String, Integer> sortedMap = unsortMap.entrySet().stream()
            .sorted(Map.Entry.comparingByKey())
            .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue,
                    (oldValue, newValue) -> oldValue, LinkedHashMap::new));
6
Taras Melnyk

Dieser Code kann eine Schlüsselwertkarte in beiden Reihenfolgen sortieren, d. H. Aufsteigend und absteigend.

<K, V extends Comparable<V>> Map<K, V> sortByValues
     (final Map<K, V> map, int ascending)
{
     Comparator<K> valueComparator =  new Comparator<K>() {         
        private int ascending;
        public int compare(K k1, K k2) {
            int compare = map.get(k2).compareTo(map.get(k1));
            if (compare == 0) return 1;
            else return ascending*compare;
        }
        public Comparator<K> setParam(int ascending)
        {
            this.ascending = ascending;
            return this;
        }
    }.setParam(ascending);

    Map<K, V> sortedByValues = new TreeMap<K, V>(valueComparator);
    sortedByValues.putAll(map);
    return sortedByValues;
}

Als Beispiel:

Map<Integer,Double> recommWarrVals = new HashMap<Integer,Double>();
recommWarrVals = sortByValues(recommWarrVals, 1);  // Ascending order
recommWarrVals = sortByValues(recommWarrVals,-1);  // Descending order
5
M. Mashaye

In Java 8

Um einen Map<K, V> nach Schlüssel zu sortieren, geben Sie Schlüssel in einen List<K> ein:

List<K> result = map.keySet().stream().sorted().collect(Collectors.toList());

Um einen Map<K, V> nach Schlüssel zu sortieren, fügen Sie die Einträge in einen List<Map.Entry<K, V>> ein:

List<Map.Entry<K, V>> result =
    map.entrySet()
       .stream()
       .sorted(Map.Entry.comparingByKey())
       .collect(Collectors.toList());

Last but not least: Um strings locale-sensitive zu sortieren, verwenden Sie eine Collator (Comparator) -Klasse

Collator collator = Collator.getInstance(Locale.US);
collator.setStrength(Collator.PRIMARY); // case insensitive collator

List<Map.Entry<String, String>> result =
    map.entrySet()
       .stream()
       .sorted(Map.Entry.comparingByKey(collator))
       .collect(Collectors.toList());
5
Oleksandr
List<String> list = new ArrayList<String>();
Map<String, String> map = new HashMap<String, String>();
for (String str : map.keySet()) {
 list.add(str);
}
Collections.sort(list);
for (String str : list) {
 System.out.println(str);
}
1
Manoj Singh

Wir können den Schlüssel auch mit der Arrays.sort-Methode sortieren.

Map<String, String> map = new HashMap<String, String>();
Object[] objArr = new Object[map.size()];
for (int i = 0; i < map.size(); i++) {
objArr[i] = map.get(i);
}
Arrays.sort(objArr);
for (Object str : objArr) {
System.out.println(str);
}
0
Manoj Singh

In funktionalem Stil wird wie folgt sein:

 Map<String , String> nameMap = new HashMap<>();
        nameMap.put("question1","1");
        nameMap.put("question9","1");
        nameMap.put("question2","4");
        nameMap.put("question5","2");
        nameMap.entrySet().stream()
            .sorted(Comparator.comparing(x->x.getKey()))
            .map(x->x.getKey())
            .forEach(System.out::println);

Ausgabe:

frage 1 

frage 2

frage5

frage 9

0
Common Man

In Java 8 können Sie auch .stream (). Sortiert () verwenden:

myMap.keySet().stream().sorted().forEach(key -> {
        String value = myMap.get(key);

        System.out.println("key: " + key);
        System.out.println("value: " + value);
    }
);
0
Jonas_Hess