Properties properties = new Properties(); Map map = new HashMap(properties);// why wrong?
java.util.Properties est une implémentation de Map et le constructeur HashMap reçoit un paramètre de type Map. Mais pourquoi faut-il convertir explicitement?
En effet, Properties étend Hashtable (qui, à son tour, implémente Map ). Vous tentez de l’inclure dans une Map . C’est donc incompatible.
Vous devez alimenter les propriétés de la chaîne une par une dans votre map …
Par exemple:
for (final Ssortingng name: properties.ssortingngPropertyNames()) map.put(name, properties.getProperty(name));
Le moyen le plus efficace de le faire est de procéder comme suit:
Properties props = new Properties(); Map map = (Map)props;
Cela convertira un Map en une map brute, ce qui est “ok” pour le compilateur (uniquement avertissement). Une fois que nous avons une Map brute, elle sera convertie en Map qui sera également “ok” (autre avertissement). Vous pouvez les ignorer avec l’annotation @SuppressWarnings({ "unchecked", "rawtypes" })
Cela fonctionnera car dans la JVM, l’object n’a pas vraiment de type générique. Les types génériques ne sont qu’une astuce qui vérifie les choses au moment de la compilation.
Si une clé ou une valeur n’est pas une chaîne, une erreur ClassCastException sera ClassCastException . Avec l’implémentation actuelle des Properties il est très improbable que cela se produise, tant que vous n’utilisez pas les méthodes d’appel mutables du super Hashtable of Properties .
Donc, ne faites pas de vilaines choses avec votre instance Propriétés, c’est la voie à suivre.
Que dis-tu de ça?
Map properties = new Properties(); Map map = new HashMap(properties);
Va provoquer un avertissement, mais fonctionne sans itérations.
properties.entrySet().stream().collect( Collectors.toMap( e -> e.getKey().toSsortingng(), e -> e.getValue().toSsortingng() ) );
Properties implémentent Map – non Map .
Vous essayez d’appeler ce constructeur:
public HashMap(Map extends K,? extends V> m)
… avec K et V sous forme de Ssortingng .
Mais Map n’est pas une Map extends String, ? extends String>Map extends String, ? extends String>Map extends String, ? extends String> … il peut contenir des clés et des valeurs autres que des chaînes.
Cela fonctionnerait:
Map
… mais ça ne vous serait pas utile.
Fondamentalement, les Properties n’auraient jamais dû être une sous-classe de HashTable … c’est le problème. Depuis la v1, il est toujours possible de stocker des clés et des valeurs non-Ssortingng, bien que cela soit contraire à l’intention. Si la composition avait été utilisée à la place, l’API n’aurait pu fonctionner qu’avec des clés / valeurs de chaîne, et tout se serait bien passé.
Vous pouvez vouloir quelque chose comme ceci:
Map map = new HashMap(); for (Ssortingng key : properties.ssortingngPropertyNames()) { map.put(key, properties.getProperty(key)); }
Properties properties = new Properties(); Map map = Maps.fromProperties(properties);
Si vous savez que votre object Properties contient uniquement des entrées , vous pouvez utiliser un type brut:
Properties properties = new Properties(); Map map = new HashMap((Map) properties);
Le problème est que Properties implémente Map , alors que le constructeur HashMap attend une Map extends String, ? extends String>Map extends String, ? extends String>Map extends String, ? extends String> .
Cette réponse explique cette décision (plutôt contre-intuitive). En bref: avant Java 5, Properties implémentait Map (car il n’y avait pas de génériques à l’époque). Cela signifie que vous pouvez placer n’importe quelObject dans un object Properties . Ceci est encore dans la documentation:
Étant donné que Properties hérite de Hashtable , les méthodes put et putAll peuvent être appliquées à un object Properties . Leur utilisation est fortement déconseillée car ils permettent à l’appelant d’insérer des entrées dont les clés ou les valeurs ne sont pas des Ssortingng . La méthode setProperty doit être utilisée à la place.
Pour maintenir la compatibilité avec ceci, les concepteurs n’ont eu d’autre choix que de le faire hériter de Map en Java 5. Il s’agit d’un résultat regrettable de la recherche d’une compatibilité ascendante intégrale.
Si vous n’utilisez jamais des propriétés de chaîne dans votre object Properties , vous devriez pouvoir faire une dissortingbution non contrôlée dans votre constructeur:
Map map = new HashMap( (Map) properties);
ou sans copie:
Map map = (Map) properties;
Ceci est uniquement dû au fait que le constructeur de HashMap requirejs un argument de type générique Map et que Properties implémente Map.
Cela fonctionnera, mais avec un avertissement
Properties properties = new Properties(); Map map = new HashMap(properties);
Première chose,
La classe de propriétés est basée sur Hashtable et non sur Hashmap. La classe de propriétés étend fondamentalement Hashtable
Il n’y a pas de tel constructeur dans la classe HashMap qui prend un object de propriétés et vous renvoie un object hashmap. Donc, ce que vous faites n’est pas correct. Vous devriez être capable de convertir l’object de propriétés en référence hashtable.
j’utilise ceci:
for (Map.Entry entry:properties.entrySet()) { map.put((Ssortingng) entry.getKey(), (Ssortingng) entry.getValue()); }