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

Python Discussion :

Retours ligne, différence Windows Linux


Sujet :

Python

  1. #1
    Expert éminent

    Homme Profil pro
    Inscrit en
    Octobre 2008
    Messages
    4 302
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Octobre 2008
    Messages : 4 302
    Points : 6 782
    Points
    6 782
    Par défaut Retours ligne, différence Windows Linux
    Salut,

    Le bloc-note de Windows affichant de manière illisible les fichiers créés sous Linux, j'ai installé Gedit et Eric4 pour Windows.

    En ce moment, j'ai un code qui crée des fichiers Python en utilisant le retour ligne du système, soit '\r\n' dans ce cas ci.

    Ces fichiers s'affichent correctement avec le bloc-note, mais présentent un double retour ligne avec Gedit et Eric. Si je vérifie les longueurs des lignes de texte elles ont bien deux caractères supplémentaires non visibles, ce qui est attendu, alors pouquoi ces lignes vides intercalées ?

    Dans les paramètres de l'éditeur de Gedit il n'est nulle part question de cela. Quand à Eric, la vie est trop courte pour s'aventurer dans l'éditeur de configuration.

    Y aurait-il une astuce ou bien "faut faire avec" ?

  2. #2
    Membre averti
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2013
    Messages
    247
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 42
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Mai 2013
    Messages : 247
    Points : 406
    Points
    406
    Par défaut
    Si tu as une ligne vide, c'est que l'interprétation des 2 caractères \r et \n se font de manière séparée

    Je te conseillerais d'utiliser le bon vieux Notepad++ qui te permet facilement de visualiser ces fichiers et tu pourra facilement afficher/modifier l'encodage des fins de lignes

    Désolé de ne pas t'apporter une réponse plus précise à ton problème

  3. #3
    Expert éminent

    Homme Profil pro
    Inscrit en
    Octobre 2008
    Messages
    4 302
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Octobre 2008
    Messages : 4 302
    Points : 6 782
    Points
    6 782
    Par défaut
    Merci mais avec Notepad++ ce n'est guère différent.

    Pour simplifier, la question se pose ainsi, avec ce code:
    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
     
    # -*- coding: utf-8 -*-
     
    import os
    L_SEP = os.linesep
     
    def write():
        strings = ['# -*- coding: utf-8 -*-\n',
                    'import os\n',
                    'import sys\n']
        with open('writetest.py', 'w') as outf:
            for s in strings:
                outf.write(s.replace('\n', L_SEP))
     
    write()
    Donc, on crée un fichier de trois lignes dont les fins de lignes sont ceux du système.

    La syntaxe s.replace('\n', L_SEP) et due au fait que le code doit être portable.

    Le fichier créé s'ouvre normalement avec le bloc-note Windows mais avec un double saut de ligne dans Gedit, Eric4 ... et Notepad++

    Pour info, les fichiers créés s'exécutent sans problème.

  4. #4
    Membre éprouvé

    Homme Profil pro
    Diverses et multiples
    Inscrit en
    Mai 2008
    Messages
    662
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Diverses et multiples

    Informations forums :
    Inscription : Mai 2008
    Messages : 662
    Points : 1 273
    Points
    1 273
    Par défaut
    Sous gedit (version linux, en tout cas), on choisit l’encodage et le type de fin de ligne au moment de l’enregistrement. Donc pour modifier celui d’un fichier ouvert, il faut faire “enregistrer sous”, conserver le même nom de fichier, et modifier les réglages sus-cités dans le bas du dialogue d’enregistrement…

  5. #5
    Membre averti
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2013
    Messages
    247
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 42
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Mai 2013
    Messages : 247
    Points : 406
    Points
    406
    Par défaut
    Si tu fais L_SEP='', est ce que tu as encore un retour à la ligne mais sans saut de ligne?

    Sinon en faisant (ça fait un petit moment que j'ai pas fait de python alors je suis pas sûr de la synthaxe):
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    s.replace(/\s*$/, '')
    s .= L_SEP
    normalement, \s devrait enlever tous les espaces, retour charriot en fin de ligne et ensuite il suffit de remettre le saut de ligne que tu veux

  6. #6
    Expert éminent

    Homme Profil pro
    Inscrit en
    Octobre 2008
    Messages
    4 302
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Octobre 2008
    Messages : 4 302
    Points : 6 782
    Points
    6 782
    Par défaut
    @ mont29, Oui mais dans mon cas le fichier est écrit par un script et non créé avec l'éditeur.
    Donc si j'ouvre le fichier dans cet éditeur et que je le réenregistre avec le bon code de fin de ligne, le code est enregistré avec le même double saut de ligne qui a été créé lors de l'ouverture.

    Le problème est dans l'ouverture du fichier, pourquoi différemment dans MS Bloc-notes et les autres éditeurs ?

    @ 6ril23, L_SEP doit être ce qui est donné par os.linesep, portabilité oblige.

  7. #7
    Membre averti
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2013
    Messages
    247
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 42
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Mai 2013
    Messages : 247
    Points : 406
    Points
    406
    Par défaut
    Citation Envoyé par VinsS Voir le message
    @ 6ril23, L_SEP doit être ce qui est donné par os.linesep, portabilité oblige.
    oui j'avais bien compris ce que tu souhaites faire mais en faisant le test avec L_SEP='', si tu as encore un retour à la ligne, c'est que tu as bien un autre caractère de retour charriot et donc qu'il faudra mettre \n\n ou \r\n... dans ton replace

  8. #8
    Expert éminent

    Homme Profil pro
    Inscrit en
    Octobre 2008
    Messages
    4 302
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Octobre 2008
    Messages : 4 302
    Points : 6 782
    Points
    6 782
    Par défaut
    ben si je fais ceci:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
     
    def count():
        with open('c:\\Users\\Vincent\\writetest.py', 'r') as inf:
            lines = inf.readlines()
        for l in lines:
            print(l, len(l))
     
    count()
    J'obtiens cela:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    ('# -*- coding: utf-8 -*-\r\n', 25)
    ('import os\r\n', 11)
    ('import sys', 10)
    Ce qui semble être attendu, non?

  9. #9
    Membre expérimenté
    Homme Profil pro
    Inscrit en
    Mars 2007
    Messages
    941
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Mars 2007
    Messages : 941
    Points : 1 384
    Points
    1 384
    Par défaut
    Lorsque le fichier est ouvert en mode texte (ce qui est le cas dans le code posté), Python convertit automatiquement les '\n' dans la version adaptée à l'OS. Donc si ton code est exécuté sous Windows, ils seront remplacés par '\r\n', pas besoin de le faire manuellement. Maintenant, si tu veux vraiment contrôler toi-même les caractères de fin de ligne, ouvre le fichier en mode binaire ("wb") plutôt qu'en mode texte.

  10. #10
    Membre averti
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2013
    Messages
    247
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 42
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Mai 2013
    Messages : 247
    Points : 406
    Points
    406
    Par défaut
    Citation Envoyé par VinsS Voir le message
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    ('# -*- coding: utf-8 -*-\r\n', 25)
    ('import os\r\n', 11)
    ('import sys', 10)
    Ce qui semble être attendu, non?
    Oui ça me semble normal.
    par contre si tu appliques ton code précédent:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    'import os\r\n'       # Remplacement du '\n' par '\r\n'
    va devenir --> 'import os\r\r\n'
    et ça ne fonctionnera pas comme voulu (sur un fichier Mac, il n'y aura pas de '\n' donc pas de remplacement)

    je pense que si tu fais comme ci-dessous ça peut fonctionner
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    string='import os\r\n'
    string.rstrip()                 # Suppression des '\t', ' ', '\n', '\r'
    string .= os.linesep         # Ajout a la chaine du retour charriot selon l'OS
    Edit: ah oui en connaissant le fonctionnement réel des fonctions c'est plus simple
    merci @dividee pour cette subtilité à l'ouverture

  11. #11
    Expert éminent

    Homme Profil pro
    Inscrit en
    Octobre 2008
    Messages
    4 302
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Octobre 2008
    Messages : 4 302
    Points : 6 782
    Points
    6 782
    Par défaut
    @ dividee, En fait le code original est effectivement ouvert en mode binaire, les fins de lignes sont normalisés à '\n' parce que le fichier doit être parser par le module tokenise.

    Ce n'est qu'après traitement qu'il faut rétablir le fin de ligne correct selon l'os.

    Cette façon de faire m'est pas de ma main mais copiée directement du programme 2to3, et, en fait tout se déroule sans aucun problème, sauf que le développeur ne se contente pas du bloc-notes de Win pour éditer ses scripts et le double ligne dans eric ou autres, ça la fout mal.

    Sur la ML de python on me dit que
    Then it seems like there is an issue with your text editors that do not play nicely with DOS-style line endings.
    J'aimerai bien, ça m'arrangerais de dire que c'est la faute a l'éditeur.

    Quelqu'un a testé le petit code, et ouvert le fichier dans un éditeur ?

    On parle de Windows, pas Linux, hein.

  12. #12
    Membre expérimenté
    Homme Profil pro
    Inscrit en
    Mars 2007
    Messages
    941
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Mars 2007
    Messages : 941
    Points : 1 384
    Points
    1 384
    Par défaut
    Oui j'ai testé le code du troisième post en j'obtiens CR+CR+LF ('\r\r\n') comme fin de ligne, ce qui explique le double retour de ligne.
    Si j'ouvre le fichier en écriture mode binaire:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    ...
    with open('writetest.py', 'wb') as outf:
    ...
    Là j'obtiens correctement CR+LF.
    Et j'obtiens la même chose en ouvrant en mode texte et sans faire le replace:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     with open('writetest.py', 'w') as outf:
        for s in strings:
            outf.write(s)

  13. #13
    Expert éminent

    Homme Profil pro
    Inscrit en
    Octobre 2008
    Messages
    4 302
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Octobre 2008
    Messages : 4 302
    Points : 6 782
    Points
    6 782
    Par défaut
    Citation Envoyé par dividee Voir le message
    Oui j'ai testé le code du troisième post en j'obtiens CR+CR+LF ('\r\r\n') comme fin de ligne, ce qui explique le double retour de ligne.
    Ça par contre, je ne l'ai jamais eu.

    Simplifions le code:
    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
     
    # -*- coding: utf-8 -*-
     
    import os
     
    path = 'c:\\Users\\Vincent\\writetest.py'
     
    def write():
        strings = ['# -*- coding: utf-8 -*-', 'import os', 'import sys']
        txt = os.linesep.join(strings)
        with open(path, 'w') as outf:
            outf.write(txt)
     
    def count():
        with open(path, 'r') as inf:
            for l in inf:
                print(l, len(l))
     
    write()
    count()
    Dans la console:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    ('# -*- coding: utf-8 -*-\r\n', 25)
    ('import os\r\n', 11)
    ('import sys', 10)
    Toujours correct, mais seul le bloc-notes de Win l'ouvre correctement

  14. #14
    Expert éminent

    Homme Profil pro
    Inscrit en
    Octobre 2008
    Messages
    4 302
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Octobre 2008
    Messages : 4 302
    Points : 6 782
    Points
    6 782
    Par défaut
    Bon ben la solution était trop simple, il suffit d'écrire le fichier en mode binaire.

    Ça ne change rien sous Linux, sous Windows, les lignes affichent un \n comme séparateur de lignes mais, malgré cela, ça s'ouvre enfin correctement avec tous les éditeurs.

  15. #15
    Membre expérimenté
    Homme Profil pro
    Inscrit en
    Mars 2007
    Messages
    941
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Mars 2007
    Messages : 941
    Points : 1 384
    Points
    1 384
    Par défaut
    Sous Windows, quand le fichier est ouvert en mode texte, le \n est automatiquement converti en CR+LF à l'écriture, et l'opération inverse a lieu à la lecture. C'est pourquoi ton test de lecture n'indiquait pas le problème. Le fichier contenait bien CR+CR+LF, qui devenait \r (le premier CR) suivi de \n (le couple CR+LF qui suit). Pour voir réellement ce que contenait le fichier je l'ai ouvert avec un éditeur hexa (le plugin hexa pour notepad++).

Discussions similaires

  1. Différences compilation Linux(make/gcc)/Windows(mingw)
    Par boelraty dans le forum Débuter
    Réponses: 2
    Dernier message: 28/07/2010, 10h46
  2. Différence de police Windows/Linux
    Par Digilougm dans le forum Mise en page CSS
    Réponses: 2
    Dernier message: 03/12/2009, 01h48
  3. Différence entre Linux et Windows avec array_walk_recursive
    Par fredu dans le forum PHP & Base de données
    Réponses: 5
    Dernier message: 16/05/2009, 13h45
  4. Réponses: 7
    Dernier message: 11/07/2007, 23h01
  5. Différence entre assembleur Windows/Linux
    Par MonsieurAk dans le forum x86 32-bits / 64-bits
    Réponses: 3
    Dernier message: 29/03/2006, 10h19

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