J'ai cette carte Map<String, Set<Integer>> myMap;
, maintenant je dois interagir avec elle, comment puis-je le faire?
Les clés sont: "Apple", "orange", "raisin", etc.
Chaque ensemble contiendra des nombres aléatoires: 1-9
J'ai besoin de créer une carte (HashMap ou TreeMap) qui contient des chaînes pour les clés et des ensembles pour les valeurs. Je dois retourner l'ensemble donné une clé. Je dois aussi pouvoir remplir chaque ensemble avec plusieurs numéros basés sur une clé. Vous ne savez pas comment aborder ce problème. Des pensées?
Pas difficile si je comprends bien.
Map<String, Set<Integer>> reqdMap = new HashMap<String, Set<Integer>>();
//Form the set corresponding to Apple.
Set<Integer> appleSet = new HashSet<Integer>();
appleSet.add(1);
...
reqdMap.put("Apple", appleSet);
//To Retrieve
appleSet = reqdMap.get("Apple");
Il convient de garder à l'esprit que la valeur sera initialement nulle et que, dès la première utilisation d'une clé, vous devrez l'initialiser:
Map<String,Set<Integer>> map;
Pour ajouter un numéro à la clé, vous devez procéder comme suit:
String key = "Apple"; // for example
Set<Integer> set = map.get(key);
if (set == null) {
set = new HashSet<Integer>();
map.put(key, set);
}
set.add(5);
Malheureusement, partout où vous interagissez avec l'ensemble, vous devez effectuer un contrôle nul. Par exemple, si vous voulez vérifier si une certaine clé est associée à un certain nombre, vous ne pouvez pas le faire en toute sécurité:
if (map.get(key).contains(number)) // not safe
parce que l'appel à get()
peut renvoyer null
(s'il n'y a pas d'entrée pour la clé) et que vous obtiendrez une NullPointerException
.
Il existe un moyen de rendre votre carte très pratique à utiliser en internalisant le contrôle null à l'intérieur de la carte, de sorte qu'un appel à get()
renvoie toujours un ensemble non nul; créez une classe anonyme qui remplace get()
en conséquence:
Map<String,Set<Integer>> map = new HashMap<String,Set<Integer>> () {
@Override
public Set<Integer> get(Object key) {
Set<Integer> set = super.get(key);
if (set == null) {
set = new HashSet<Integer>();
put(key, set);
}
return set;
}
}
Avec cela en place, votre code principal devient beaucoup plus simple et clair. Ajouter:
map.get(key).add(number);
Vérifier:
if (map.get(key).contains(number)) // now safe
Le code de vérification nul n'est plus nécessaire.
——
Pour traiter le problème de la saisie de valeur nulle lors de l'ajout à l'ensemble:
map.computeIfAbsent( key, k -> new HashSet<>() ).add(number);
et pour la vérification null safe:
if ( map.getOrDefault(key, Collections.emptySet() ).contains(number))
Pourquoi ne pas regarder ceci:
https://github.com/google/guava/wiki/NewCollectionTypesExplained#multimap
MultiMap
vous permet de stocker plusieurs valeurs pour une clé donnée de manière très efficace.
Dans votre cas, le grand avantage est que vous n'êtes pas obligé de récupérer une valeur (Set
) à partir d'une clé donnée afin de lui ajouter des valeurs.
En effet, il vous suffit d’ajouter la valeur à la clé comme si vous traitiez avec "monovalue" et elle sera automatiquement ajoutée à la set
en arrière-plan.
Map<String, Set<Integer>> mapOfSets = new HashMap<String, Set<Integer>>();
Set<Integer> numberSet = new HashSet<Integer>();
//put a set into the map
mapOfSets.put("key", numberSet);
//get a set out of the map
Set<Integer> set = mapOfSets.get("key");
Si vous souhaitez ajouter plusieurs nombres à un ensemble avec une seule méthode, essayez ceci:
Map<String, Set<Integer>> map; // Definition
public void addValues(String key, Integer... values) {
map.get(key).addAll(values);
}
Ainsi, lorsque vous devez ajouter plusieurs numéros pour une touche, vous pouvez effectuer un appel comme ceci:
addValues("Apple", 1, 2, 4, 6, 8);
Une ligne au lieu de 5.
ceci est juste un exemple classe complète. il suffit de l'exécuter et d'y travailler pour en savoir plus sur ce problème
public class Tester5 {
/**
* @param args
*/
public static void main(String[] args) {
//"Apple", "orange", "grape", etc. Each set will contain random numbers: 1, 2, 3, 4, 5, 6, 7, 8, 9
Random ran = new Random();
Map<String, Set<Integer>> map= new HashMap<String, Set<Integer>>();
String keys[]= {"Apple", "orange", "grape"};
for(String key : keys) {
Set<Integer> integers= new HashSet<Integer>();
for(int i = 0; i < 10; i++) {
integers.add(ran.nextInt(9)+1);
}
map.put(key, integers);
}
System.out.println(map.toString());
}
}
Map<String,Set<Integer>> map;
Set<Integer> set = map.get("Apple");
J'omets la population réelle de map
puisque le PO est comment get
l'ensemble c'est-à-dire la valeur