2017-08-22 4 views
0

J'ai le code suivant pour un ArrayListMultimap imbriqué:Comment obtenir la valeur dans un imbriquée `ArrayListMultimap`

Multimap<String, Multimap<Integer, String>> doubleMultiMap = ArrayListMultimap.create(); 
    Multimap<Integer, String> doc = ArrayListMultimap.create(); 
    doc.put(1, "ABC"); 
    doc.put(2, "BCD"); 
    doc.put(1, "XYZ"); 
    doubleMultiMap.put("D123", doc); 

    doc = ArrayListMultimap.create(); 
    doc.put(1, "John"); 
    doc.put(2, "Jane"); 
    doc.put(2, "George"); 
    doubleMultiMap.put("J123", doc); 
    System.out.println(doubleMultiMap.get("D123")); 

Pour doubleMultiMap.get("D123") j'obtenir le résultat que [{1=[ABC, XYZ], 2=[BCD]}]

Mais comment obtenir la valeur touches D123, 1. J'ai essayé d'utiliser (doubleMultiMap.get("D123")).get(1) mais ce n'est pas supporté.

Mise à jour: Ce que j'essaie de réaliser est quelque chose comme ci-dessous. Si imbriqué Multimap n'est pas idéal, quelle alternative pourrais-je utiliser?

enter image description here

+2

Avez-vous vraiment besoin d'une double carte multiple? Votre exemple et votre code essayé ressemble à ce que vous voulez en fait 'Map >'. – Tom

+1

Puis-je ajouter que l'utilisation d'un Multimap imbriqué est une très mauvaise idée? Un multimap concerne la structure de données la plus complexe que vous devriez utiliser. –

+2

@Tom cela équivaut à l'interface 'Multitable' qui est [discuté depuis des années] (https://github.com/google/guava/issues/902) –

Répondre

1

Si vous n'avez pas besoin Table méthodes comme ligne ou spécifique de l'accès à la colonne (et il semble que vous ne le faites pas, puisque vous voulez accéder D123, 1), la clé composée pour Multimap est la solution. Créez une chaîne de stockage de classe simple et un nombre entier avec hashCode et equals appropriés et utilisez normalement multimap. En supposant que votre nom de classe de clé composé est Key (vous devriez penser à meilleur), vous devriez être en mesure de faire quelque chose comme ceci:.

//given 
ListMultimap<Key, String> multimap = ArrayListMultimap.create(); // note ListMultimap 
multimap.put(new Key("D123", 1), "ABC"); 
multimap.put(new Key("D123", 2), "BCD"); 
multimap.put(new Key("D123", 1), "XYZ"); 
multimap.put(new Key("J123", 1), "John"); 
multimap.put(new Key("J123", 2), "Jane"); 
multimap.put(new Key("J123", 2), "George"); 
//when 
List<String> values = multimap.get(new Key("D123", 1)); 
//then 
assertThat(values).containsExactly("ABC", "XYZ"); 

Si vous avez besoin d'accéder by row ou by column (ex obtenir la cartographie complète de la colonne 2 qui dans votre cas aurait des clés "D123" et "J123"), alors vous pouvez régler avec Table<String, Integer, List<String>> et prendre soin de créer des listes dans les valeurs de tableau sur demande (malheureusement, il n'y a pas d'interface computeIfAbsent dans Table).

Troisième option serait de discuter Multitable dans this Guava issue, comme mentionné par @SeanPatrickFloyd dans le commentaire ci-dessus.

+0

Quand vous avez dit d'utiliser 'hashcode' et' equals', est-ce comme ceci: http://tutorials.jenkov.com/java-collections/hashcode-equals.html – SachiDangalla

+0

suivant le contrat entre ['hashCode'] (https://docs.oracle.com/javase/7/docs/api/java/lang/Object.html#hashCode%28%29) et [' equals'] (https : //docs.oracle.com/javase/7/docs/api/java/lang/Object.html#equals%28java.lang.Object%29). La plupart des IDE peuvent générer ces méthodes pour vous. – Xaerxess

1

En fait, ce qui est un get rendement Collection (de Multimap dans votre cas). Take a look:

Collection get (@Nullable clé K)

Renvoie une vue collection des valeurs associées à la clé dans cette multimap, le cas échéant. Notez que lorsque containsKey (key) est false, ce retourne une collection vide, pas null.

Les modifications apportées à la collection retournée mettront à jour le multimap sous-jacent , et vice versa.

Pour obtenir le imbriquée Multimap faire:

Iterator<Multimap<Integer, String>> iter = doubleMultiMap.get("D123").iterator(); 
Multimap<Integer, String> nested = iter.next(); 
+0

Vous pouvez obtenir une liste via l'interface 'ListMultimap'. Mais l'index correct serait 0. – shmosel