Créer et initialiser des cartes dans Groovy vs Java


  • FrançaisFrançais


  • J’ai récemment exploré certaines des différences entre Java et Groovy lors de la création et de l’initialisation de listes et de la construction de listes au moment de l’exécution. J’ai observé les facilités simples fournies par Groovy à ces fins par rapport à la complexité requise en Java.

    Dans cet article, j’examine la création et l’initialisation de cartes en Java et Groovy. Les cartes offrent la possibilité de développer des structures que vous pouvez rechercher par clé. Et si la clé est trouvée, cela renvoie le évaluer associé à cette clé. Aujourd’hui, les cartes sont implémentées dans de nombreux langages de programmation, dont Java et Groovy, mais aussi Python (où elles sont appelées dictionnaires), Perl, awk et bien d’autres. Un autre terme couramment utilisé pour décrire les cartes est tableaux associatifsque vous pouvez lire dans cet article Wikipédia. Les cartes Java et Groovy sont bien générales, permettant aux clés et aux valeurs d’être toutes les classes qui étendent le Object classer.

    Installer Java et Groovy

    Groovy est basé sur Java et nécessite également une installation Java. Une version récente et décente de Java et de Groovy peut se trouver dans les référentiels de votre distribution Linux. Ou, vous pouvez installer Groovy en suivant les instructions sur le lien mentionné ci-dessus. Une bonne alternative pour les utilisateurs de Linux est SDKManName, que vous pouvez utiliser pour obtenir plusieurs versions de Java, Groovy et de nombreux autres outils associés. Pour cet article, j’utilise les versions du SDK de :

    • Java : version 11.0.12-open d’OpenJDK 11 ;
    • Groovy : version 3.0.8.

    Retour au problème

    Java offre un certain nombre de façons d’instancier et d’initialiser des cartes, et depuis Java 9, plusieurs nouvelles approches ont été ajoutées. Le candidat le plus évident est la méthode statique java.util.Map.of() que vous pouvez utiliser comme suit :

    var m1 = Map.of(
        "AF", "Afghanistan",
        "AX", "Åland Islands",
        "AL", "Albania",
        "DZ", "Algeria",
        "AS", "American Samoa",
        "AD", "Andorra",
        "AO", "Angola",
        "AI", "Anguilla",
        "AQ", "Antarctica");

    System.out.println("m1 = " + m1);
    System.out.println("m1 is an instance of " + m1.getClass());

    Il se trouve que Map.of() utilisé de cette manière comporte deux restrictions importantes. Tout d’abord, l’instance de carte que vous créez de cette manière est immuable. Deuxièmement, de cette façon, vous pouvez fournir au maximum 20 arguments, représentant dix paires clé-valeur.

    Essayez d’ajouter les dixième et onzième paires, dites « AG », « Antigua-et-Barbuda » et « AR », « Argentine » pour voir ce qui se passe. Vous verrez le compilateur Java chercher une version de Map.of() qui accepte 11 paires et échoue.

    Un rapide coup d’oeil la documentation de java.util.Map montre la raison de cette deuxième limitation et montre un moyen de sortir de cette énigme :

    var m2 = Map.ofEntries(
        Map.entry("AF", "Afghanistan"),
        Map.entry("AX", "Åland Islands"),
        Map.entry("AL", "Albania"),
        Map.entry("DZ", "Algeria"),
        Map.entry("AS", "American Samoa"),
        Map.entry("AD", "Andorra"),
        Map.entry("AO", "Angola"),
        Map.entry("AI", "Anguilla"),
        Map.entry("AQ", "Antarctica"),
        Map.entry("AG", "Antigua and Barbuda"),
        Map.entry("AR", "Argentina"),
        Map.entry("AM", "Armenia"),
        Map.entry("AW", "Aruba"),
        Map.entry("AU", "Australia"),
        Map.entry("AT", "Austria"),
        Map.entry("AZ", "Azerbaijan"),
        Map.entry("BS", "Bahamas"),
        Map.entry("BH", "Bahrain"),
        Map.entry("BD", "Bangladesh"),
        Map.entry("BB", "Barbados")
    );
           
    System.out.println("m2 = " + m2);
    System.out.println("m2 is an instance of " + m2.getClass());

    Tant que je n’ai pas besoin de modifier par la suite le contenu de la carte créée et initialisée avec Map.ofEntries(), c’est une bonne solution. Notez ci-dessus que plutôt que d’utiliser Map.of() comme dans le premier exemple, j’ai utilisé Map.ofEntries().

    Cependant, en supposant que je veuille créer et initialiser une instance de carte avec quelques entrées et ajouter plus tard à cette carte, je dois faire quelque chose comme ceci :

    var m3 = new HashMap<String,String>(Map.ofEntries(
        Map.entry("AF", "Afghanistan"),
        Map.entry("AX", "Åland Islands"),
        Map.entry("AL", "Albania"),
        Map.entry("DZ", "Algeria"),
        Map.entry("AS", "American Samoa"),
        Map.entry("AD", "Andorra"),
        Map.entry("AO", "Angola"),
        Map.entry("AI", "Anguilla"),
        Map.entry("AQ", "Antarctica"),
        Map.entry("AG", "Antigua and Barbuda"),
        Map.entry("AR", "Argentina"),
        Map.entry("AM", "Armenia"),
        Map.entry("AW", "Aruba"),
        Map.entry("AU", "Australia"),
        Map.entry("AT", "Austria"),
        Map.entry("AZ", "Azerbaijan"),
        Map.entry("BS", "Bahamas"),
        Map.entry("BH", "Bahrain"),
        Map.entry("BD", "Bangladesh"),
        Map.entry("BB", "Barbados")
    ));

    System.out.println("m3 = " + m3);
    System.out.println("m3 is an instance of " + m3.getClass());

    m3.put("BY", "Belarus");
    System.out.println("BY: " + m3.get("BY"));

    Ici, en utilisant la carte immuable créée par Map.ofEntries() comme argument à la HashMap constructeur, j’en crée une copie mutable, que je peux ensuite modifier, par exemple, avec le put() méthode.

    Jetez un œil à la version Groovy de ce qui précède :

    def m1 = [
        "AF": "Afghanistan",
        "AX": "Åland Islands",
        "AL": "Albania",
        "DZ": "Algeria",
        "AS": "American Samoa",
        "AD": "Andorra",
        "AO": "Angola",
        "AI": "Anguilla",
        "AQ": "Antarctica",
        "AG": "Antigua and Barbuda",
        "AR": "Argentina",
        "AM": "Armenia",
        "AW": "Aruba",
        "AU": "Australia",
        "AT": "Austria",
        "AZ": "Azerbaijan",
        "BS": "Bahamas",
        "BH": "Bahrain",
        "BD": "Bangladesh",
        "BB": "Barbados"]

    println "m1 = $m1"
    println "m1 is an instance of ${m1.getClass()}"

    m1["BY"] = "Belarus"
    println "m1 = $m1"

    En un coup d’œil, vous voyez que Groovy utilise le def mot-clé plutôt que var– bien que dans le dernier modèle de Groovy (version 3+), il soit possible d’utiliser var au lieu.

    Vous voyez également que vous pouvez créer une représentation cartographique en plaçant une liste de paires clé-valeur entre crochets. De plus, l’instance de liste ainsi créée est très utile pour plusieurs raisons. Premièrement, il est mutable, et deuxièmement, c’est une instance de LinkedHashMap, qui préserve l’ordre d’insertion. Ainsi, lorsque vous exécutez la version Java et imprimez la variable m3vous voyez:

    m3 = {BB=Barbados, BD=Bangladesh, AD=Andorra, AF=Afghanistan, AG=Antigua and Barbuda, BH=Bahrain, AI=Anguilla, AL=Albania, AM=Armenia, AO=Angola, AQ=Antarctica, BS=Bahamas, AR=Argentina, AS=American Samoa, AT=Austria, AU=Australia, DZ=Algeria, AW=Aruba, AX=Åland Islands, AZ=Azerbaijan}

    Lorsque vous exécutez la version Groovy, vous voyez :

    m1 = [AF:Afghanistan, AX:Åland Islands, AL:Albania, DZ:Algeria, AS:American Samoa, AD:Andorra, AO:Angola, AI:Anguilla, AQ:Antarctica, AG:Antigua and Barbuda, AR:Argentina, AM:Armenia, AW:Aruba, AU:Australia, AT:Austria, AZ:Azerbaijan, BS:Bahamas, BH:Bahrain, BD:Bangladesh, BB:Barbados]

    Une fois de plus, vous voyez comment Groovy simplifie la situation. La syntaxe est très simple, rappelant un peu les dictionnaires de Python, et nul besoin de retenir les différentes contorsions nécessaires si vous avez une liste initiale de plus de dix paires. Notez que nous utilisons l’expression :

    m1[“BY”] = “Belarus”

    Plutôt que le Java :

    m1.put(“BY”, “Belarus”)

    De plus, la carte est mutable par défaut, ce qui est sans doute bon ou mauvais, selon les besoins. Je pense que ce qui me dérange dans le “défaut immuable” de la situation Java, c’est qu’il n’y a pas quelque chose comme Map.mutableOfMutableEntries(). Cela oblige le programmeur, qui vient de comprendre comment déclarer et initialiser une carte, à changer de vitesse et à réfléchir à la manière de convertir la carte immuable dont il dispose en quelque chose de mutable. Je m’interroge aussi un peu sur l’entreprise de créer quelque chose d’immuable juste pour le jeter.

    Une autre chose à laquelle il faut penser est les crochets car la recherche de clé fonctionne pour remplacer les deux put() et get() en Java, vous pouvez donc écrire :

    m1[“ZZ”] = m1[“BY”]

    Au lieu de:

    m1.put(“ZZ”,m1.get(“BY”))

    Parfois, il est agréable de penser aux clés et à leurs valeurs de la même manière que vous pensez aux champs dans l’instance d’une classe. Imaginez que vous vouliez définir un tas de propriétés : dans Groovy, cela pourrait ressembler à :

    def properties = [
          verbose: true,
          debug: false,
          logging: false]

    Et puis plus tard, vous pouvez le changer comme suit :

    properties.verbose = false

    Cela fonctionne car, tant que la clé suit certaines règles, vous pouvez omettre les guillemets et utiliser l’opérateur point au lieu des crochets. Bien que cela puisse être très utile et agréable, cela signifie également que pour utiliser la valeur d’une variable comme valeur clé dans une représentation cartographique, vous devez mettre la variable entre parenthèses, comme :

    def myMap = [(k1): v1, (k2): v2]

    C’est le bon moment pour rappeler au lecteur assidu que Groovy est particulièrement bien adapté à la scénarisation. Souvent, les cartes sont un élément clé des scripts, fournissant des tables de recherche et fonctionnant généralement comme une base de données en mémoire. L’exemple que j’ai utilisé ici est un sous-ensemble des codes de pays à deux caractères ISO 3166 et des noms de pays. Les codes sont familiers à tous ceux qui accèdent aux noms d’hôte Internet dans les pays du monde entier, ce qui pourrait constituer une partie utile d’un utilitaire de script qui examine les noms d’hôte Internet dans les fichiers journaux pour en savoir plus sur la répartition géographique des utilisateurs.

    Ressources géniales

    le Site Apache Groovy a beaucoup de grande documentation. Une autre excellente ressource Groovy est M. Haki. le Site de Baeldung fournit de nombreuses informations utiles sur Java et Groovy. Et une très bonne raison d’apprendre Groovy est de continuer et d’apprendre Graalsqui est un framework Web complet merveilleusement productif construit sur d’excellents composants comme Hibernate, Spring Boot et Micronaut.

    Source

    La Rédaction

    L'équipe rédactionnnelle du site

    Pour contacter personnellement le taulier :

    Laisser un commentaire

    Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *

    Copy code