IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Langage Perl Discussion :

Incompréhension du pragma use utf8


Sujet :

Langage Perl

  1. #1
    Expert éminent sénior Avatar de disedorgue
    Homme Profil pro
    Ingénieur intégration
    Inscrit en
    Décembre 2012
    Messages
    4 277
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur intégration
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Décembre 2012
    Messages : 4 277
    Points : 12 722
    Points
    12 722
    Par défaut Incompréhension du pragma use utf8
    Bonjour,

    J'ai un souci de compréhension sur le comportement de perl a propos du pragma utf8, voici le cas:
    Juste pour montré que le caractère est bien en utf8:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    $ echo -n "é" | hexdump -C
    00000000  c3 a9                                             |..|
    00000002
    ici, perl le traite bien comme un caractère utf8:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    $ perl -e 'print "é"' | hexdump -C
    00000000  c3 a9                                             |..|
    00000002
    Maintenant, lorsque l'on rajoute le pragma use utf8, perl me le transforme en autre chose que de l'utf8:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    $ perl -e 'use utf8;print "é"' | hexdump -C
    00000000  e9                                                |.|
    00000001
    J'ai ce cas quand j'ai des chaines directement déclarée dans un scalair, par contre, si je récupère la chaine depuis un fichier, dans les 2 cas (avec ou sans utf8), le caractère reste inchangé:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    $ echo -n "é" | perl -ne 'print $_' | hexdump -C
    00000000  c3 a9                                             |..|
    00000002
    $ echo -n "é" | perl -ne 'use utf8;print $_' | hexdump -C
    00000000  c3 a9                                             |..|
    00000002
    Ce que je ne comprend pas, c'est le cas de la déclaration dans un scalair, j'aurais plus pensé intuitivement à un comportement inverse ou identique.

    Si quelqu'un a une réponse, je suis preneur.
    Cordialement.

  2. #2
    Membre chevronné Avatar de dmganges
    Homme Profil pro
    Retraité. Ne recherche pas un emploi.
    Inscrit en
    Septembre 2011
    Messages
    1 392
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 71
    Localisation : France, Hérault (Languedoc Roussillon)

    Informations professionnelles :
    Activité : Retraité. Ne recherche pas un emploi.
    Secteur : Service public

    Informations forums :
    Inscription : Septembre 2011
    Messages : 1 392
    Points : 2 044
    Points
    2 044
    Par défaut
    Bonjour,

    C'est étonnant en effet et je n'ai pas d'explication très rationnelle...

    J'ai ce cas quand j'ai des chaines directement déclarée dans un scalair, par contre, si je récupère la chaine depuis un fichier, dans les 2 cas (avec ou sans utf8), le caractère reste inchangé:
    En ce qui me concerne j'ai rencontré des pb en traitant des caractères arabes.
    Je veille a être cohérent partout, c'est à dire :
    - Fichier en lecture et/ou écriture en UTF-8
    - J'utilise toujours le pragma :
    dans mes fichiers sources.pl, justement pour avoir des scalaires qui sortent correctement,
    - Mais de plus je dois sauvegarder mes sources.pl en UTF-8 NO BOM (avec Ultraedit) UTF-8 devrait suffire...

    Ceci étant, dans tes exemples, chez moi en Perl v5.22.2 j'ai une anomalie de signalée pour ton cas précis :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    perl -ne 'use utf8;print "é"' | hexdump -C
    Pour tenter une explication :
    - Lorsque la source est un fichier .pl il y a bien interprétation et conversion
    - Lorsque la source est injectée depuis le fichier STDIN par un echo elle sort correctement
    - Lorsque la source n'est pas injectée mais communiquée à Perl directement par print il n'y aurait pas d'interprétation
    En ligne de commande le pragma qui doit interpréter les caractères provenant d'une source ne fonctionnerait pas.
    Mais c'est juste histoire de retomber sur mes pattes

    Donc pour ton cas, veille à sauvegarder tes sources en UTF-8

  3. #3
    Expert éminent sénior Avatar de disedorgue
    Homme Profil pro
    Ingénieur intégration
    Inscrit en
    Décembre 2012
    Messages
    4 277
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur intégration
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Décembre 2012
    Messages : 4 277
    Points : 12 722
    Points
    12 722
    Par défaut
    Sauf que:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    $ cat essaix.pl
    #!/usr/bin/env perl
     
    use strict;
    use warnings;
    use utf8;
     
    my $toto='é';
    print $toto . "\n";
    Le type du fichier:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    $ file -i essaix.pl
    essaix.pl: text/plain; charset=utf-8
    un hexdump pour bien voir que le "é" est bien en utf8:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    $ hexdump -C essaix.pl
    00000000  23 21 2f 75 73 72 2f 62  69 6e 2f 65 6e 76 20 70  |#!/usr/bin/env p|
    00000010  65 72 6c 0a 0a 75 73 65  20 73 74 72 69 63 74 3b  |erl..use strict;|
    00000020  0a 75 73 65 20 77 61 72  6e 69 6e 67 73 3b 0a 75  |.use warnings;.u|
    00000030  73 65 20 75 74 66 38 3b  0a 0a 6d 79 20 24 74 6f  |se utf8;..my $to|
    00000040  74 6f 3d 27 c3 a9 27 3b  0a 70 72 69 6e 74 20 24  |to='é';.print $|
    00000050  74 6f 74 6f 20 2e 20 22  5c 6e 22 3b 0a           |toto . "\n";.|
    0000005d
    Et si on exécute le script, le caractère est modifié tout comme la ligne de commande:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    $ ./essaix.pl | hexdump -C
    00000000  e9 0a                                             |..|
    00000002
    Et si on retire le pragma utf8, le caractère reste inchangé...
    Cordialement.

  4. #4
    Membre chevronné Avatar de dmganges
    Homme Profil pro
    Retraité. Ne recherche pas un emploi.
    Inscrit en
    Septembre 2011
    Messages
    1 392
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 71
    Localisation : France, Hérault (Languedoc Roussillon)

    Informations professionnelles :
    Activité : Retraité. Ne recherche pas un emploi.
    Secteur : Service public

    Informations forums :
    Inscription : Septembre 2011
    Messages : 1 392
    Points : 2 044
    Points
    2 044
    Par défaut
    Oui, j'ai oublié le pb Invite_de_commande/Terminal/Console

    L'invite de commande... n'étant pas compatibles UTF-8...

    Dans tous mes scripts je colle le Super, le Fameux... ... ActiverAccents(); de dijbril

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    #!/usr/bin/env perl
     
    use strict;
    use warnings;
    use utf8;
     
     
    # Pour avoir les accents dans l'invite de commande (Console/Terminal)
    ActiverAccents();
     
     
    my $toto='é';
    print $toto . "\n";
     
    #==============================================================
    # Pour avoir les accents sur la console DOS
    # http://perl.developpez.com/faq/perl/?page=Terminal#AccentsDOS
    #==============================================================
    sub ActiverAccents {
    	my $encodage;
    	# Windows
      	if ( lc($^O ) eq 'mswin32') {                           # Si je suis sur Windows
    		eval {
    			my ($codepage) = ( `chcp` =~ m/:\s+(\d+)/ );          # On récupère le nombre que renvoie chcp dans une invite de commande
    			                                                      # exemple : Page de codes active*: 437
    			$encodage = "cp$codepage";                            # On accole ce nombre au libellé "cp" de façon avoir cp437
    			foreach my $h ( \*STDOUT, \*STDERR, \*STDIN, ) {      # pour les fichiers spéciaux sortie_Ecran, Sortie_Erreur, Clavier_Entrée
    				binmode $h, ":encoding($encodage)";                 # djibril modifie l'encodage ;)
    			}
    		};	
    	}
    	else {                                                    # SINON je suis dans Unix / Linux
    		$encodage = `locale charmap`;                           # On récupère l'encodage par défaut, mais avec la commande qui va bien
    		eval {
    			foreach my $h ( \*STDOUT, \*STDERR, \*STDIN, ) {      # djibril modifie l'encodage des fichiers spéciaux ;)
    				binmode $h, ":encoding($encodage)";
    			}
    		};	
    	}
      return $encodage;                                         # Retourne le bon encodage suivant l'OS
    }
     
    #Sinon petit rappel pour info :
    #ü 	\x81 	à 	\x85 	è 	\x8A
    #é 	\x82 	ç 	\x87 	ï 	\x8B
    #â 	\x83 	ê 	\x88 	î 	\x8C
    #ä 	\x84 	ë 	\x89
    [Edit 13:13] Ajout Terminal Cygwin
    et dans un terminal ont voit bien dans le cat que les caractères UTF-8 sont mal interprétés
    par contre avec la fonction ActiverAccents();
    le print est OK

  5. #5
    Expert éminent sénior Avatar de disedorgue
    Homme Profil pro
    Ingénieur intégration
    Inscrit en
    Décembre 2012
    Messages
    4 277
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur intégration
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Décembre 2012
    Messages : 4 277
    Points : 12 722
    Points
    12 722
    Par défaut
    Ok, mais par exemple, le code unicode et utf8 du "é" est:
    Unicode
    code point
    character UTF-8
    (in literal)
    name
    U+00E9 é \xc3\xa9 LATIN SMALL LETTER E WITH ACUTE
    Et au vu de ce que me retourne le cas avec le pragma utf8, celui-ci me transforme le caractère utf8 en unicode.
    D'ailleurs, je viens de trouver ce que fait perl lorsque l'on utilise le pragma utf8:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    $ perl -e 'use utf8; $toto="é"; print $toto . "\n"'| hexdump -C
    00000000  e9 0a                                             |..|
    00000002
    $ perl -e 'use utf8; $toto="é"; utf8::decode($toto);print $toto . "\n"' | hexdump -C
    00000000  e9 0a                                             |..|
    00000002
    $ perl -e 'use utf8; $toto="é"; utf8::encode($toto);print $toto . "\n"' | hexdump -C
    00000000  c3 a9 0a                                          |é.|
    00000003
    Celui-ci fait un decode de la chaine, ce qui fait que l'on obtient le \xe9, alors qu'intuitivement, on s'attendrait à ce qu'il fasse, en fait, un encode...

    Après, est-ce normal d'avoir ce comportement, là cela me dépasse
    Cordialement.

  6. #6
    Membre chevronné Avatar de dmganges
    Homme Profil pro
    Retraité. Ne recherche pas un emploi.
    Inscrit en
    Septembre 2011
    Messages
    1 392
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 71
    Localisation : France, Hérault (Languedoc Roussillon)

    Informations professionnelles :
    Activité : Retraité. Ne recherche pas un emploi.
    Secteur : Service public

    Informations forums :
    Inscription : Septembre 2011
    Messages : 1 392
    Points : 2 044
    Points
    2 044
    Par défaut
    Oh !
    Entre le normal et l'intuitif il y a souvent un univers de différence... et pas seulement en informatique

    Trêve de plaisanterie c'est bien parce que je n'obtenais pas ce que j’imaginais intuitivement que je me suis imposé l'UTF-8 sur toute la ligne : Fichiers E/S & code.
    Ce n'est pas ce qu'il y a de plus économique en taille de fichier, mais au moins je sais (à peu près) où j'en suis

    Quand j'ai commencé en informatique les caractères étaient codés sur 6 bits on appelait çà l'EBCDIC, là on avait pas même droit aux accents...
    et comme on avait pas beaucoup de mémoire on coupaient les caractères en deux, trois ou quatre (c'est le cas de le dire...) pour stocker le numérique...
    Bull avait même inventé l'octet de 9 bits , avec un mots machine de 4 caractères = 36 bits, on y stockaient soit 9 caractères alphabétiques, soit 12 caractères numériques... l'opulence QUOI !
    On passait déjà notre temps à faire des conversions...

    Il faut comprendre qu'on a à disposition un demi-siècle de codification des caractères.
    Les personnes qui ont dû faire les choix qui nous étonnent, avaient elles, les contraintes de la compatibilité ascendante...
    C'est devenu un millefeuille, mais je ne me sens pas de taille à leur jeter une pierre...

    Pourquoi on ne peut toujours pas écrire en arabe, en tibétain, en thaïlandais, en japonnais... dans une invite de commande, une console, un terminal ?
    Les intéressés eux-mêmes ne s'en plaignent pas
    Tu n'en demandes pas tant, parce que tu n'en as pas l’utilité, pourtant ça serait "normal" !

    J'ai dans mes favoris l'ensemble des codes, dès que j'ai un doute ou un pb, je vérifie plutôt que de faire confiance à mon intuition, parce qu'à chaque fois que je le fais je me plante

    Dans les derniers exemples que tu as collé, on a non seulement rien qui correspond à nos intuitions mais aussi des anomalies de signalées...

    Perso je suis devenu docile, je ne me pose plus la question de la normalité, surtout en informatique, je suis conscient que j'ai été formaté par les ordinateurs
    Alors je me fie à Spinoza :
    "Par réalité et par perfection j'entends la même chose."
    Désolé, je m'en tire comme je peux

    Bonne continuation !

  7. #7
    Rédacteur/Modérateur

    Avatar de Lolo78
    Homme Profil pro
    Conseil - Consultant en systèmes d'information
    Inscrit en
    Mai 2012
    Messages
    3 612
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Conseil - Consultant en systèmes d'information
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Mai 2012
    Messages : 3 612
    Points : 12 469
    Points
    12 469
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par disedorgue Voir le message
    Et au vu de ce que me retourne le cas avec le pragma utf8, celui-ci me transforme le caractère utf8 en unicode.
    D'ailleurs, je viens de trouver ce que fait perl lorsque l'on utilise le pragma utf8:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    $ perl -e 'use utf8; $toto="é"; print $toto . "\n"'| hexdump -C
    00000000  e9 0a                                             |..|
    00000002
    $ perl -e 'use utf8; $toto="é"; utf8::decode($toto);print $toto . "\n"' | hexdump -C
    00000000  e9 0a                                             |..|
    00000002
    $ perl -e 'use utf8; $toto="é"; utf8::encode($toto);print $toto . "\n"' | hexdump -C
    00000000  c3 a9 0a                                          |é.|
    00000003
    Celui-ci fait un decode de la chaine, ce qui fait que l'on obtient le \xe9, alors qu'intuitivement, on s'attendrait à ce qu'il fasse, en fait, un encode...
    Non, le pragma utf8 se contente d'interpréter le code de ton programme (donc, y compris les chaînes de caractères contenues dans tes variables) comme de l'UTF8. Mais il n'effectue aucune sorte de conversion, et n'a pas en lui-même d'influence sur les entrées et sorties.

    Je te conseille de lire ceci: http://perl.developpez.com/tutoriels...e-guide-perl5/, peut-être que ça clarifiera la question.

    Sinon, je n'en dis pas plus sur ton problème, car je ne suis pas sûr de bien le comprendre.

  8. #8
    Expert éminent sénior Avatar de disedorgue
    Homme Profil pro
    Ingénieur intégration
    Inscrit en
    Décembre 2012
    Messages
    4 277
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur intégration
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Décembre 2012
    Messages : 4 277
    Points : 12 722
    Points
    12 722
    Par défaut
    Ok, le pragma se contente d'interprêter ce que je lui donne, j'ai commencer à lire le lien que tu as mis et que je trouve très interressant mais je reste pour l'instant dubitatif sur mon cas.
    Prenons un script simple:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    #!/usr/bin/perl 
    use strict;
    use warnings;
    use utf8;
     
    print \n";
    passons se script sous xxd pour vérifier que le "é" dans le print est bien de l'utf8:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    $ xxd simple.pl 
    0000000: 2321 2f75 7372 2f62 696e 2f70 6572 6c20  #!/usr/bin/perl 
    0000010: 0a75 7365 2073 7472 6963 743b 0a75 7365  .use strict;.use
    0000020: 2077 6172 6e69 6e67 733b 0a75 7365 2075   warnings;.use u
    0000030: 7466 383b 0a0a 7072 696e 7420 22c3 a95c  tf8;..print "..\
    0000040: 6e22 3b0a                                n";.
    Et maintenant executons le perl et filtrons le résultat avec xxd (là, je m'attend à avoir le code utf8 "c3a9" ) :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    $ perl simple.pl | xxd
    0000000: e90a                                     ..
    Et non, j'ai le code unicode "e9".
    Maintenant, le même code perl, sans le pragma utf8, me retourne bien le code utf8 "c3a9".
    Par contre, cette "transformation" ne se fait pas si la donnée vient d'un flux ou qu'on la code explicitement \xc3\xa9.
    Et si j'avais mis le "é" mais sous sa forme unicode, perl avec le pragma utf8 me génère une erreur de type:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Malformed UTF-8 character (unexpected non-continuation byte 0x5c, immediately after start byte 0xe9) at simple.pl line 6.
    Cordialement.

  9. #9
    Expert confirmé

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Avril 2009
    Messages
    3 577
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 58
    Localisation : France, Bas Rhin (Alsace)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Avril 2009
    Messages : 3 577
    Points : 5 753
    Points
    5 753
    Par défaut
    C'est ton print (qui écris sur le filehandle STDOUT) qui transforme ton code UTF8 en un code propre au terminal.
    As-tu essayé en forçant le codage de STDOUT avec binmode ?

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    $ perl -E 'use strict;
    use warnings;
    use utf8;
    binmode STDOUT, ":utf8";
    print "é\n";' | xxd
    0000000: c3a9 0a                                  ...
    Plus j'apprends, et plus je mesure mon ignorance (philou67430)
    Toute technologie suffisamment avancée est indiscernable d'un script Perl (Llama book)
    Partagez vos problèmes pour que l'on partage ensemble nos solutions : je ne réponds pas aux questions techniques par message privé
    Si c'est utile, say

  10. #10
    Expert éminent sénior Avatar de disedorgue
    Homme Profil pro
    Ingénieur intégration
    Inscrit en
    Décembre 2012
    Messages
    4 277
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur intégration
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Décembre 2012
    Messages : 4 277
    Points : 12 722
    Points
    12 722
    Par défaut
    Ok, j'y ai cru, puis sur mon problème réel, cela ne fonctionne pas, mais cela me donne des piste de compréhension:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    use strict;
    use warnings;
    binmode STDOUT, ":utf8";
    my $xx=crypt("é","\$6\$rounds=5000\$ABCDFE0123456789");
    print "$xx\n";
    $xx=crypt("é","\$6\$rounds=5000\$ABCDFE0123456789");
    print "$xx\n";
    use utf8;
    $xx=crypt("é","\$6\$rounds=5000\$ABCDFE0123456789");
    print "$xx\n";
    en dump hexa pour être sur que le caractère est bien l'utf8 'c3a9':
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    xxd essai.pl
    0000000: 7573 6520 7374 7269 6374 3b0a 7573 6520  use strict;.use
    0000010: 7761 726e 696e 6773 3b0a 6269 6e6d 6f64  warnings;.binmod
    0000020: 6520 5354 444f 5554 2c20 223a 7574 6638  e STDOUT, ":utf8
    0000030: 223b 0a6d 7920 2478 783d 6372 7970 7428  ";.my $xx=crypt(
    0000040: 22c3 a922 2c22 5c24 365c 2472 6f75 6e64  "▒.","\$6\$round
    0000050: 733d 3530 3030 5c24 4142 4344 4645 3031  s=5000\$ABCDFE01
    0000060: 3233 3435 3637 3839 2229 3b0a 7072 696e  23456789");.prin
    0000070: 7420 2224 7878 5c6e 223b 0a24 7878 3d63  t "$xx\n";.$xx=c
    0000080: 7279 7074 2822 c3a9 222c 225c 2436 5c24  rypt("▒.","\$6\$
    0000090: 726f 756e 6473 3d35 3030 305c 2441 4243  rounds=5000\$ABC
    00000a0: 4446 4530 3132 3334 3536 3738 3922 293b  DFE0123456789");
    00000b0: 0a70 7269 6e74 2022 2478 785c 6e22 3b0a  .print "$xx\n";.
    00000c0: 7573 6520 7574 6638 3b0a 2478 783d 6372  use utf8;.$xx=cr
    00000d0: 7970 7428 22c3 a922 2c22 5c24 365c 2472  ypt("▒.","\$6\$r
    00000e0: 6f75 6e64 733d 3530 3030 5c24 4142 4344  ounds=5000\$ABCD
    00000f0: 4645 3031 3233 3435 3637 3839 2229 3b0a  FE0123456789");.
    0000100: 7072 696e 7420 2224 7878 5c6e 223b 0a    print "$xx\n";.
    et à l'execution, on a:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    perl essai.pl
    $6$rounds=5000$ABCDFE0123456789$xoi750QKPEIml29NS8dC9PdNFyMo401iixmjyHdD0YGHzgWlhuObYz8tpB7GBRxBrML2YpbDzLqzb99R23.Hs1
    $6$rounds=5000$ABCDFE0123456789$xoi750QKPEIml29NS8dC9PdNFyMo401iixmjyHdD0YGHzgWlhuObYz8tpB7GBRxBrML2YpbDzLqzb99R23.Hs1
    $6$rounds=5000$ABCDFE0123456789$FGXiGqo1FFHpQ9B.M80h/T9oODc/vypxlQM3pEhSNDBNQ9ehrWXboWhJu5.5WUnLV0AS4skf0ONPKQRDULtdK.
    ici, on voit que le dernier crypt est différent et pourtant on crypt la même chose, mais quand je rajoute le pragma utf8, il me crypte en unicode:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    perl -E 'print crypt("\xc3\xa9","\$6\$rounds=5000\$ABCDFE0123456789");'
    $6$rounds=5000$ABCDFE0123456789$xoi750QKPEIml29NS8dC9PdNFyMo401iixmjyHdD0YGHzgWlhuObYz8tpB7GBRxBrML2YpbDzLqzb99R23.Hs1
    perl -E 'print crypt("\xe9","\$6\$rounds=5000\$ABCDFE0123456789");'
    $6$rounds=5000$ABCDFE0123456789$FGXiGqo1FFHpQ9B.M80h/T9oODc/vypxlQM3pEhSNDBNQ9ehrWXboWhJu5.5WUnLV0AS4skf0ONPKQRDULtdK.
    Cordialement.

  11. #11
    Expert confirmé

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Avril 2009
    Messages
    3 577
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 58
    Localisation : France, Bas Rhin (Alsace)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Avril 2009
    Messages : 3 577
    Points : 5 753
    Points
    5 753
    Par défaut
    J'avoue ne pas comprendre.
    Je ne sais pas si ça peut aider, mais il y a une note en fin d'aide à la fonction crypt:
    If using crypt() on a Unicode string (which potentially has
    characters with codepoints above 255), Perl tries to make sense of
    the situation by trying to downgrade (a copy of) the string back
    to an eight-bit byte string before calling crypt() (on that copy).
    If that works, good. If not, crypt() dies with "Wide character in
    crypt".
    Sinon, as-tu essayé en utilisant une fonction perso autre que crypt (et qui ferait par exemple une simple concaténation avec des [ ] autour ? histoire de dédouaner crypt).
    Plus j'apprends, et plus je mesure mon ignorance (philou67430)
    Toute technologie suffisamment avancée est indiscernable d'un script Perl (Llama book)
    Partagez vos problèmes pour que l'on partage ensemble nos solutions : je ne réponds pas aux questions techniques par message privé
    Si c'est utile, say

  12. #12
    Membre chevronné Avatar de dmganges
    Homme Profil pro
    Retraité. Ne recherche pas un emploi.
    Inscrit en
    Septembre 2011
    Messages
    1 392
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 71
    Localisation : France, Hérault (Languedoc Roussillon)

    Informations professionnelles :
    Activité : Retraité. Ne recherche pas un emploi.
    Secteur : Service public

    Informations forums :
    Inscription : Septembre 2011
    Messages : 1 392
    Points : 2 044
    Points
    2 044
    Par défaut
    Bonsoir,
    Je ne comprends pas davantage mais :
    Que l'on écrive sur STDOUT ou dans un fichier l'ajout du pragma use utf8 modifie le comportement !

    - la seule façon d'avoir un fichier Sortie.txt correct (avec accent)
    + Bien que l'ouverture du fichier soit faites avec '>:utf8'
    Il faut le pragma dans le source.pl pour avoir l'accent !

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    use strict;
    use warnings;
    binmode STDOUT, ":utf8";
    my $xx="é";
    print "$xx\n";
    $xx="é";
    print "$xx\n";
    use utf8;
    $xx="é";
    print "$xx\n";
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    use strict;
    use warnings;
    #binmode STDOUT, ":utf8";
    my $xx="é";
    print "$xx\n";
    $xx="é";
    print "$xx\n";
    use utf8;
    $xx="é";
    print "$xx\n";
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    use strict;
    use warnings;
     
    open ( my $fh_sortie, '>:utf8', 'Sortie.txt' )
    	or die ( "Imposible d'ouvrir le fichier $!" );
     
    my $xx="é";
    print $fh_sortie "$xx\n";
    $xx="é";print $fh_sortie "$xx\n";
    use utf8;
    $xx="é";
    print $fh_sortie "$xx\n";
    Dans mes mésaventures j'en ai déduit que lorsqu'on travaille en utf8, il faut veiller à l'être partout :
    - écriture dans les fichiers '>:utf8'
    - code source.pl avec pragma use utf8
    - code source sauvegardé en utf8 (NO BOM)

    Mais ne me demandez pas pourquoi
    [Edit 18:58] pour coller bonne image !

  13. #13
    Expert éminent sénior Avatar de disedorgue
    Homme Profil pro
    Ingénieur intégration
    Inscrit en
    Décembre 2012
    Messages
    4 277
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur intégration
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Décembre 2012
    Messages : 4 277
    Points : 12 722
    Points
    12 722
    Par défaut
    Qu'est-ce que vous ne comprenez pas ? mon problème ou le comportement du pragma utf8 sur les scalairs renseigné en dur ?

    Car perso, je comprends très bien que le pragma utf8 modifie le comportement, ce que je ne comprends pas, c'est qu'on lui passe en dure de l'utf8 et qu'il le transforme en unicode et que si on lui passe de l'unicode, il nous envoie une erreur.

    Un autre exemple sans crypt:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    $ perl -e '$_=qq(tité); s/\xe9/i/ ; print $_."\n"'
    tité
    $ perl -e 'use utf8;$_=qq(tité); s/\xe9/i/ ; print $_."\n"'
    titi
    Comme on peut le voir encore, le pragma utf8, modifie le \xc3\xa9 en \xe9 (donc de l'utf8 en unicode).
    Cordialement.

  14. #14
    Membre chevronné Avatar de dmganges
    Homme Profil pro
    Retraité. Ne recherche pas un emploi.
    Inscrit en
    Septembre 2011
    Messages
    1 392
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 71
    Localisation : France, Hérault (Languedoc Roussillon)

    Informations professionnelles :
    Activité : Retraité. Ne recherche pas un emploi.
    Secteur : Service public

    Informations forums :
    Inscription : Septembre 2011
    Messages : 1 392
    Points : 2 044
    Points
    2 044
    Par défaut
    Citation Envoyé par disedorgue
    Car perso, je comprends très bien que le pragma utf8 modifie le comportement, ce que je ne comprends pas, c'est qu'on lui passe en dure de l'utf8 et qu'il le transforme en unicode et que si on lui passe de l'unicode, il nous envoie une erreur.
    J'en étais arrivé là également, il y a 3, 4 ans... et je n'ai toujours pas compris le pourquoi !
    j'en étais resté à :
    Pourquoi à t-il besoin du pragma utf8 alors qu'effectivement le code est en utf8 et qu'on écrit dans les fichiers en utf8
    (J'efface les images devenues inutiles).

  15. #15
    Expert confirmé

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Avril 2009
    Messages
    3 577
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 58
    Localisation : France, Bas Rhin (Alsace)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Avril 2009
    Messages : 3 577
    Points : 5 753
    Points
    5 753
    Par défaut
    Citation Envoyé par disedorgue Voir le message
    Car perso, je comprends très bien que le pragma utf8 modifie le comportement, ce que je ne comprends pas, c'est qu'on lui passe en dure de l'utf8 et qu'il le transforme en unicode et que si on lui passe de l'unicode, il nous envoie une erreur.
    Il me semble, mais c'est à vérifier (je l'avais lu dans les docs je crois), que perl stocke les chaines dans des variables sous un certain format (peut-être unicode). Le comportement entre une chaine litérale et une chaine stockée dans une variable peut alors être différent.
    Plus j'apprends, et plus je mesure mon ignorance (philou67430)
    Toute technologie suffisamment avancée est indiscernable d'un script Perl (Llama book)
    Partagez vos problèmes pour que l'on partage ensemble nos solutions : je ne réponds pas aux questions techniques par message privé
    Si c'est utile, say

  16. #16
    Membre chevronné Avatar de dmganges
    Homme Profil pro
    Retraité. Ne recherche pas un emploi.
    Inscrit en
    Septembre 2011
    Messages
    1 392
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 71
    Localisation : France, Hérault (Languedoc Roussillon)

    Informations professionnelles :
    Activité : Retraité. Ne recherche pas un emploi.
    Secteur : Service public

    Informations forums :
    Inscription : Septembre 2011
    Messages : 1 392
    Points : 2 044
    Points
    2 044
    Par défaut
    Citation Envoyé par Philou67430 Voir le message
    Il me semble, mais c'est à vérifier (je l'avais lu dans les docs je crois), que perl stocke les chaines dans des variables sous un certain format (peut-être unicode). Le comportement entre une chaine litérale et une chaine stockée dans une variable peut alors être différent.
    Le sujet devient presque plus philosophique qu'informatique
    Citation Envoyé par disedorgue
    Après, est-ce normal d'avoir ce comportement, là cela me dépasse
    Citation Envoyé par dmganges
    Mais ne me demandez pas pourquoi
    Alors, pour jouer je continue Philou67430 :

    Si perl stocke les chaines dans des variables sous un certain format
    l'utilisation du pragma use utf8 devient superflue, Perl 'sachant' que les variables sont toutes dans un format unique, il ne lui resterait plus qu'à appliquer d'office la conversion...

    L'interrogation de disedorgue persiste, de même que mon pourquoi
    En fait je ne me pose plus la question,
    Citation Envoyé par dmganges
    - la seule façon d'avoir un fichier Sortie.txt correct (avec accent)
    + Bien que l'ouverture du fichier soit faites avec '>:utf8'
    + ("ET que le code source soit également en utf8")
    Il faut le pragma dans le source.pl pour avoir l'accent !
    ne perd pas ton temps à me répondre

  17. #17
    Expert confirmé

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Avril 2009
    Messages
    3 577
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 58
    Localisation : France, Bas Rhin (Alsace)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Avril 2009
    Messages : 3 577
    Points : 5 753
    Points
    5 753
    Par défaut
    Citation Envoyé par dmganges Voir le message
    Si perl stocke les chaines dans des variables sous un certain format
    l'utilisation du pragma use utf8 devient superflue, Perl 'sachant' que les variables sont toutes dans un format unique, il ne lui resterait plus qu'à appliquer d'office la conversion...
    Non, l'utilisation du pragma permet d'indiquer à perl l'encodage utilisé pour le code source, de sorte que, lorsque perl va "charger" une chaine littérale, il puisse la convertir convenablement dans son format "interne".

    C'est ainsi que je comprends le pragma utf8
    Plus j'apprends, et plus je mesure mon ignorance (philou67430)
    Toute technologie suffisamment avancée est indiscernable d'un script Perl (Llama book)
    Partagez vos problèmes pour que l'on partage ensemble nos solutions : je ne réponds pas aux questions techniques par message privé
    Si c'est utile, say

  18. #18
    Membre chevronné Avatar de dmganges
    Homme Profil pro
    Retraité. Ne recherche pas un emploi.
    Inscrit en
    Septembre 2011
    Messages
    1 392
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 71
    Localisation : France, Hérault (Languedoc Roussillon)

    Informations professionnelles :
    Activité : Retraité. Ne recherche pas un emploi.
    Secteur : Service public

    Informations forums :
    Inscription : Septembre 2011
    Messages : 1 392
    Points : 2 044
    Points
    2 044
    Par défaut
    Oui c'est également comme çà que j'interprétais l'utilité du pragma jusqu'à présent...

    [Edit]
    Et donc :
    il puisse la convertir convenablement dans son format "interne".

    Me convient parfaitement

Discussions similaires

  1. use package utf8
    Par boss89 dans le forum Mise en forme
    Réponses: 3
    Dernier message: 26/07/2012, 11h19
  2. [débutant] incompréhension "using"..
    Par Arnaokee dans le forum C#
    Réponses: 8
    Dernier message: 22/07/2010, 10h23
  3. incompréhension utf8, caractère é.
    Par Sylvain__A_ dans le forum Langage
    Réponses: 6
    Dernier message: 08/12/2008, 14h13
  4. [WSAD5] probleme incompréhensible
    Par capitaine_banane dans le forum Eclipse Java
    Réponses: 5
    Dernier message: 07/04/2004, 11h56
  5. Connaitre l'unitée à ajouter dans USES
    Par DelphiCool dans le forum Langage
    Réponses: 7
    Dernier message: 01/08/2002, 13h48

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo