web-dev-qa-db-fra.com

L'ordre est-il garanti pour le retour des clés et des valeurs d'un objet LinkedHashMap?

Je sais que LinkedHashMap a un ordre d'itération prévisible (ordre d'insertion). Est-ce que le Set renvoyé par LinkedHashMap.keySet() et le Collection renvoyé par LinkedHashMap.values() maintiennent également cet ordre?

143
user256239

L'interface Carte fournit trois vues de collection , qui permettent de visualiser le contenu d'une carte comme un ensemble de clés, une collection de valeurs ou un ensemble de valeurs-clés mappages. L'ordre d'une carte est défini comme l'ordre dans lequel les itérateurs des vues de collection de la carte retournent leurs éléments. Certaines implémentations de cartes, comme la classe TreeMap, offrent des garanties spécifiques quant à leur ordre; d'autres, comme la classe HashMap, ne le font pas.

- Carte

Cette liste chaînée définit l'ordre d'itération, qui est normalement l'ordre dans lequel les clés ont été insérées dans la carte ( ordre d'insertion ).

- LinkedHashMap

Donc, oui, keySet(), values() et entrySet() (les trois vues de collection mentionnées) renvoient des valeurs dans l'ordre utilisé par la liste chaînée interne. Et oui, le JavaDoc pour Map et LinkedHashMap le garantit.

C'est le but de cette classe, après tout.

207
Powerlord

En regardant la source, on dirait que oui. keySet(), values() et entrySet() utilisent tous le même itérateur d'entrée en interne.

11
sblundy

Ne vous confondez pas avec LinkedHashMap.keySet() et LinkedHashMap.entrySet() retournant Set et donc il ne devrait pas garantir la commande!

Set est une interface avec HashSet, TreeSet etc dans ses implémentations. L'implémentation HashSet de l'interface Set ne garantit pas le classement. Mais TreeSet le fait. LinkedHashSet aussi.

Par conséquent, cela dépend de la façon dont Set a été implémenté dans LinkedHashMap pour savoir si la référence Set renvoyée garantira l'ordre ou non. J'ai parcouru le code source de LinkedHashMap, ça ressemble à ceci:

private final class KeySet extends AbstractSet<K> {...}
public abstract class AbstractSet<E> extends AbstractCollection<E> implements Set<E> {...}

Ainsi LinkedHashMap/HashMap a sa propre implémentation de Set c'est-à-dire KeySet. Ne confondez donc pas cela avec HashSet.

De plus, l'ordre est maintenu par la façon dont les éléments sont insérés dans le compartiment. Regardez la méthode addEntry(..) de LinkedHashMap et comparez-la avec celle de HashMap qui met en évidence la principale différence entre HashMap et LinkedHashMap.

7
anzaan

Vous pouvez le supposer. Le Javadoc dit "ordre d'itération prévisible", et les seuls itérateurs disponibles dans une carte sont ceux pour keySet (), entrySet () et values ​​().

Donc, en l'absence de toute autre qualification, il est clairement destiné à s'appliquer à tous ces itérateurs.

5
user207421

AFAIK ce n'est pas documenté donc vous ne pouvez pas le supposer "formellement". Il est toutefois peu probable que la mise en œuvre actuelle change.

Si vous voulez assurer l'ordre, vous pouvez parcourir les ententes de la carte et les insérer dans un ensemble trié avec une fonction d'ordre de votre choix, bien que vous paierez naturellement un coût de performance.

0
Uri