Jeu de caractères dans la commande rename

nolyann Messages postés 12 Statut Membre -  
nolyann Messages postés 12 Statut Membre -
Bonjour,

Je souhaite renommer des fichiers avec la commande rename, notamment remplacer les "e" accentués par "e", et je constate un comportement bizarre avec les jeux de caractères définis par "[]". Exemple sur un fichier nommé initialement "titié":
rename -v "s/[éè]/e/g" *
titié renamed as titiee

rename -v "s/é/e/g" *
titié renamed as titie

rename -v "s/[ie]/a/g" *
titie renamed as tataa

Pourquoi le "é" est-il remplacé par "ee" quand il est spécifié dans un intervalle comme dans l'exemple 1 alors que l'exemple 2 montre qu'il est correctement remplacé quand il est spécifié seul et que l'exemple 3 montre que l'usage d'un intervalle est correct...

7 réponses

  1. UnGars
     
    Salut,

    Parce que quand tu écris
    "s/[ie]/a/g"
    c'est le i ou le e indifféremment qui sont remplacés par le caractère a et ça autant de fois que nécessaire (présence du g en fin de syntaxe).

    Pour un remplacement, c'est y et non s qu'il faut employer et en mettant toutes les correspondances :

    $ echo 'éèêëîïôöù' | sed 'y/éèêëîïôöù/eeeeiioou/'
    eeeeiioou

    $ echo "l'été sera bientôt là." | sed 'y/éèêëîïôöà/eeeeiiooa/'
    l'ete sera bientot la.
    0
  2. nolyann Messages postés 12 Statut Membre
     
    Salut,

    Merci pour ta réponse mais je crois que tu as mal compris ma question.
    Dans mes trois exemples, je suis d'accord avec les deux derniers. Mais je ne comprends pas pourquoi dans le premier j'obtiens titiee et non pas titie. L'interprétation de la commande est "si on rencontre un é ou un è, le substituer par un e" et non pas deux...
    0
    1. UnGars
       
      Oups effectivement j'avais mal lu l'énoncé ;-(

      Par contre il semblerait que ce soit un bug du programme, qui à la base n'est peut-être pas conçu pour l'alphabet français et ses caractères accentués ;-\

      En reprenant ton exemple, et en essayant de renommer un fichier ne contenant pas la lettre voulue, voilà ce qui se passe :

      $ ls -1
      titié
      titié.txt

      $ rename -n 's/[è]/e/g' *
      titié renamed as titie▒
      titié.txt renamed as titie▒.txt

      Une substitution à lieu quand même et apparaît un caractère (non pris en charge (▒)) à la suite ;-\

      Je pense que c'est aussi un problème d'encodage. Perso je suis en
      fr_FR.UTF-8
      .

      Voilà ce que donne ce caractère en le passant à unum :

      $ ../unum.pl '▒'
      Octal Decimal Hex HTML Character Unicode
      022622 9618 0x2592 ▒ "▒" MEDIUM SHADE


      http://www.fileformat.info/info/unicode/char/2592/index.htm
      0
  3. nolyann Messages postés 12 Statut Membre
     
    Salut,
    Désolé pour mon silence durant 4 jours.
    En fait il semble que le problème existe uniquement quand le caractère à substituer est d'une part accentué et d'autre part entre crochets, même seul. Mes exemples 2 et 3 montrent que ça fonctionne en dehors de ces deux conditions. Personnellement je suis en UTF8 aussi mais en anglais. Question au passage: comment fais-tu pour connaître l'encodage? Y a-t-il une commande?

    En fait j'utilise la commande rename dans un script et je voulais cumuler les caractères accentués comme ceci:
    rename -v "s/[áàâäãÁÀÂÄÃ]/a/g" *
    rename -v "s/[éèêëẽÉÈÊËẼ]/e/g" *
    rename -v "s/[íìîïĩÍÌÎÏĨ]/i/g" *
    rename -v "s/[óòôöõÓÒÔÖÕ]/o/g" *
    rename -v "s/[úùûüũÚÙÛÜŨ]/u/g" *

    Je devrai donc les écrire dans un appel à rename séparé, ce qui va pas mal ralentir mon script. Tant pis.
    0
    1. zipe31 Messages postés 34620 Date d'inscription   Statut Contributeur Dernière intervention   6 501
       
      Je pense que le problème vient de l'UTF-8 qui encode sur 2 octets ;-\

      Question au passage: comment fais-tu pour connaître l'encodage? Y a-t-il une commande?
      Avec la commande
      locale
      :
      $ locale
      LANG=fr_FR.UTF-8
      LANGUAGE=
      LC_CTYPE="fr_FR.UTF-8"
      LC_NUMERIC="fr_FR.UTF-8"
      LC_TIME="fr_FR.UTF-8"
      LC_COLLATE="fr_FR.UTF-8"
      LC_MONETARY="fr_FR.UTF-8"
      LC_MESSAGES="fr_FR.UTF-8"
      LC_PAPER="fr_FR.UTF-8"
      LC_NAME="fr_FR.UTF-8"
      LC_ADDRESS="fr_FR.UTF-8"
      LC_TELEPHONE="fr_FR.UTF-8"
      LC_MEASUREMENT="fr_FR.UTF-8"
      LC_IDENTIFICATION="fr_FR.UTF-8"
      LC_ALL=


      Sinon avec utrac :
      $ utrac -d
      Language: French
      System: Unix
      Output charset: UTF-8
      Output EOL: LF
      Error character: '_'
      0
  4. dubcek Messages postés 18627 Date d'inscription   Statut Contributeur Dernière intervention   5 660
     
    hello
    1 caractère à la fois, ça passe
    $ ls
    aéè titié èèè
    $ rename -nv 's/é/e/g;s/è/e/g' *
    aéè renamed as aee
    titié renamed as titie
    èèè renamed as eee
    $ rename -nv 's/[éè]/e/g' *
    aéè renamed as aeeee
    titié renamed as titiee
    èèè renamed as eeeeee
    $
    0
  5. Vous n’avez pas trouvé la réponse que vous recherchez ?

    Posez votre question
  6. nolyann Messages postés 12 Statut Membre
     
    Je ne savais pas qu'on pouvais cumuler des expressions de sed dans rename. Ainsi mon script sera quand-même un peu plus rapide.
    Merci à tous pour vos réponses.
    0
  7. dubcek Messages postés 18627 Date d'inscription   Statut Contributeur Dernière intervention   5 660
     
    essayer ça pour tous les accents
    $ C1="ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖØÙÚÛÜÝÞßàáâãäåæçèéêëìíîïðñòóôõöøùúûüýþÿ"
    $ C2="AAAAAAACEEEEIIIIDNOOOOOOUUUUYPSaaaaaaaceeeeiiiionoooooouuuuyby"
    $ C3="$(for((i=0; i<${#C1}; i++)); do echo -n "s/${C1:$i:1}/${C2:$i:1}/g;"; done)"
    $ rename -nv "$C3" *

    test
    $ touch $C1
    $ ls
    ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖØÙÚÛÜÝÞßàáâãäåæçèéêëìíîïðñòóôõöøùúûüýþÿ
    $ rename -nv "$C3" *
    ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖØÙÚÛÜÝÞßàáâãäåæçèéêëìíîïðñòóôõöøùúûüýþÿ renamed as AAAAAAACEEEEIIIIDNOOOOOOUUUUYPSaaaaaaaceeeeiiiionoooooouuuuyby
    0
    1. nolyann Messages postés 12 Statut Membre
       
      Ouahhh! Très compact ton script. Un bel exemple de manipulation des chaînes de caractères sous Bash!
      Je vais m'en inspirer. Merci.
      0
  8. zipe31 Messages postés 34620 Date d'inscription   Statut Contributeur Dernière intervention   6 501
     
    Re-

    Je confirme que c'est un problème d'encodage UTF-8.
    Sur une VM avec Debian 8 en UTF-8 j'ai reconfiguré les locales :

     
    sudo dpkg-reconfigure locales


    en
    fr_FR@euro
    , redémarré la session et refait des tests :

    jp@debian8:~/trash$ locale
    LANG=fr_FR@euro
    LANGUAGE=
    LC_CTYPE="fr_FR@euro"
    LC_NUMERIC="fr_FR@euro"
    LC_TIME="fr_FR@euro"
    LC_COLLATE="fr_FR@euro"
    LC_MONETARY="fr_FR@euro"
    LC_MESSAGES="fr_FR@euro"
    LC_PAPER="fr_FR@euro"
    LC_NAME="fr_FR@euro"
    LC_ADDRESS="fr_FR@euro"
    LC_TELEPHONE="fr_FR@euro"
    LC_MEASUREMENT="fr_FR@euro"
    LC_IDENTIFICATION="fr_FR@euro"
    LC_ALL=


    jp@debian8:~/trash$ touch tétè

    jp@debian8:~/trash$ ls
    tétè

    jp@debian8:~/trash$ rename -n -v 'y/[éè]/e/' t*
    rename(tétè, tete)


    jp@debian8:~/trash$ touch tétètàtôtù

    jp@debian8:~/trash$ ls
    tétè tétètàtôtù

    jp@debian8:~/trash$ rename -n -v 'y/éèàôù/eeaou/' t*
    rename(tétè, tete)
    rename(tétètàtôtù, tetetatotu)

    0
    1. nolyann Messages postés 12 Statut Membre
       
      Merci zipe31,

      Je préssentais que l'encodage était en cause, mais je n'en étais pas sûr.
      Mais je vais quand-même conserver le mien.
      0