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

Shell et commandes GNU Discussion :

Commande echo et guillemets


Sujet :

Shell et commandes GNU

  1. #1
    Membre confirmé
    Homme Profil pro
    Inscrit en
    Juillet 2009
    Messages
    120
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Juillet 2009
    Messages : 120
    Par défaut Commande echo et guillemets
    Bonjour tout le monde. Mon problème est de quelqu'un débutant au Shell Linux

    Dans ces exemples, les mots 'coucou' et 'toi' sont séparés par plusieurs espaces (>1)

    1)
    Le shell traite l'entrée comme deux paramètres fournis à la commande echo (p1=coucou et p2=toi) d'où la sortie : coucou toi (avec un seul espace intermédiaire)

    2)
    Ici, on force le Shell à traiter l'entrée comme un seul paramètre, d'où la conservation de toutes les espaces dans la sortie (les espaces sont interprétés comme des caractères standards)


    Mais en mettant une variable intermédiaire, le fonctionnement se diffère et c'est ceci dont je ne comprends pas la raison.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    var="coucou               toi" ;   echo $var
    La sortie Shell contient qu'un seul espace entre les deux mots comme si on a fourni deux paramètres à la commande echo
    Normalement, on devrait conserver toutes les espaces à cause de la présence des guillemets !
    Quelle est l'explication ? Merci

  2. #2
    Modérateur
    Avatar de N_BaH
    Profil pro
    Inscrit en
    Février 2008
    Messages
    7 635
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2008
    Messages : 7 635
    Par défaut
    Bonjour,

    UMQ!*
    il faut toujours mettre les développements de variables entre guillemets. TOUJOURS!
    à moins de savoir pourquoi.
    --
    *Use More Quotes!
    .
    N'oubliez pas de consulter les cours shell, la FAQ, et les pages man.

  3. #3
    Membre confirmé
    Homme Profil pro
    Inscrit en
    Juillet 2009
    Messages
    120
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Juillet 2009
    Messages : 120
    Par défaut
    Désolé, mais je ne comprends pas. C'est encore flou pour moi

    La variable var contient déjà des guillemets doubles, pourquoi je dois y ajouter des autres ?! ("$var"). Peux-tu m'expliquer en détail ce qui se passe dans les deux traitements : $var et "$var"

  4. #4
    Modérateur
    Avatar de N_BaH
    Profil pro
    Inscrit en
    Février 2008
    Messages
    7 635
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2008
    Messages : 7 635
    Par défaut
    il ne faut pas confondre l'assignation (var="une variable") et le développement ("$var").

    on peut faire un parallèle avec printf (ou avec for) :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    $ printf '%s\n' "$var"
    une        variable
    $ printf '%s\n' $var
    une
    variable
    avec des guillemets, printf considère n'avoir qu'un argument (comme tu l'as dit), alors que sans guillemets printf considère qu'il y a autant d'arguments que de mots (en fonction de l'IFS).
    .
    N'oubliez pas de consulter les cours shell, la FAQ, et les pages man.

  5. #5
    Membre confirmé
    Homme Profil pro
    Inscrit en
    Juillet 2009
    Messages
    120
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Juillet 2009
    Messages : 120
    Par défaut


    Dans l'expression echo $var (sans guillemets), le Shell va développer l'expression $var. Le symbole dollar indique qu'il faut chercher le contenu de la variable var. La valeur de v est construite auparavant à l'assignation où le Shell a déjà développé l'expression "coucou toi" et a interprété les espaces comme des caractères ordinaires et (non des séparations) à cause des guillemets doubles présentes. On fournit alors à la commande echo une expression dans laquelle les espaces sont déjà interprétés ce qui rend le découpage en deux paramètres quelque chose qui n'a pas de sens.

    Je vois les étapes du traitement comme ça. Où j'ai mal compris ?

  6. #6
    Modérateur
    Avatar de N_BaH
    Profil pro
    Inscrit en
    Février 2008
    Messages
    7 635
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2008
    Messages : 7 635
    Par défaut
    au moment de l'assignation, le shell ne développe rien. On lui donne une chaîne, et il la garde au chaud.
    C'est lors du développement, s'il n'y a pas de guillemets, qu'il fait les ... développements.

    on a eu le cas il y a quelques jours :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    $ ls -1
    monFichier.txt
    $ var=*.txt
    $ echo "$v" #où l'on voit ce que contient la variable
    *.txt
    $ echo $v #où l'on voit comment le shell développe le contenu de la variable
    monFichier.txt
    $
    .
    N'oubliez pas de consulter les cours shell, la FAQ, et les pages man.

  7. #7
    Membre confirmé
    Homme Profil pro
    Inscrit en
    Juillet 2009
    Messages
    120
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Juillet 2009
    Messages : 120
    Par défaut
    Ah. Ça avance. C'est la dernière question :

    On lui donne une chaîne, et il la garde au chaud :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    La chaîne ici est   "coucou                  toi".  Avec des guillemets, tu es d'accord avec moi ?
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Donc echo $var est équivalent à echo "coucou                       toi"
    Je n'ai rien développé jusqu'à maintenant. J'ai seulement remplacé $v par la chaîne donnée auparavant

    Cette chaîne peut-être :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    "coucou          toi"       ou       "coucou          toi"!         ou    ....
    Et dans tous les cas

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    echo  "coucou           toi"              ou                    echo   "coucou          toi"!
    (avec les développements maintenant)

    Toutes les espaces sont gardées.

  8. #8
    Expert confirmé Avatar de Flodelarab
    Homme Profil pro
    Inscrit en
    Septembre 2005
    Messages
    5 283
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Charente (Poitou Charente)

    Informations forums :
    Inscription : Septembre 2005
    Messages : 5 283
    Par défaut
    Bonjour

    Donc echo $var est équivalent à echo "coucou toi"
    Je ne suis pas d'accord avec cette phrase. Tu devrais plus considérer le caractère éphémère des "double quotes". Quand tu assignes var="coucou toi", ce qui est en mémoire, c'est coucou toi. Les guillemets ont disparus. Quand tu tapes echo $var, plus aucun "double quote" à l'horizon. Et quand tu tapes echo "$var", il va prendre ta variable comme un tout, mais il ne va pas garder tes "double quotes". Ainsi, les 2 expressions, qui sont dans la citation, ne sont pas équivalentes car la première saccage les espaces, alors que la seconde les garde.

    Rappel : Pour savoir ce qu'exécute l'intérpréteur, on peut faire set -x.
    Exemple :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    $ echo *
    2023.08.08-14257-ITEMA_23455467-2022F23173S0305-22.mp3 2023.08.08-22831-ITEMA_23455547-2023C45541E0106-21.mp3 2023.08.09-10351-ITEMA_23454311-2023C3500E0079-21.mp3 2023.08.10-10351-ITEMA_23454311-2023C3500E0080-21.mp3 enTransit gt2013.08.12-14373-ITEMA_23404867-2013C49904E0031-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0032-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0033-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0034-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0035-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0036-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0037-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0038-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0039-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0040-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0041-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0042-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0043-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0044-21.mp3 gt2023.06.29-14373-ITEMA_23440573-2022C49904E0001-21.mp3 gt2023.06.29-14373-ITEMA_23440573-2022C49904E0002-21.mp3 gt2023.06.29-14373-ITEMA_23440573-2022C49904E0003-21.mp3 gt2023.06.29-14373-ITEMA_23440573-2022C49904E0004-21.mp3 gt2023.08.07-14373-ITEMA_23454835-2022C49904E0001-21.mp3 sav
    $ set -x
    $ echo *
    +15:08:00 echo 2023.08.08-14257-ITEMA_23455467-2022F23173S0305-22.mp3 2023.08.08-22831-ITEMA_23455547-2023C45541E0106-21.mp3 2023.08.09-10351-ITEMA_23454311-2023C3500E0079-21.mp3 2023.08.10-10351-ITEMA_23454311-2023C3500E0080-21.mp3 enTransit gt2013.08.12-14373-ITEMA_23404867-2013C49904E0031-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0032-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0033-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0034-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0035-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0036-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0037-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0038-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0039-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0040-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0041-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0042-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0043-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0044-21.mp3 gt2023.06.29-14373-ITEMA_23440573-2022C49904E0001-21.mp3 gt2023.06.29-14373-ITEMA_23440573-2022C49904E0002-21.mp3 gt2023.06.29-14373-ITEMA_23440573-2022C49904E0003-21.mp3 gt2023.06.29-14373-ITEMA_23440573-2022C49904E0004-21.mp3 gt2023.08.07-14373-ITEMA_23454835-2022C49904E0001-21.mp3 sav
    2023.08.08-14257-ITEMA_23455467-2022F23173S0305-22.mp3 2023.08.08-22831-ITEMA_23455547-2023C45541E0106-21.mp3 2023.08.09-10351-ITEMA_23454311-2023C3500E0079-21.mp3 2023.08.10-10351-ITEMA_23454311-2023C3500E0080-21.mp3 enTransit gt2013.08.12-14373-ITEMA_23404867-2013C49904E0031-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0032-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0033-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0034-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0035-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0036-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0037-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0038-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0039-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0040-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0041-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0042-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0043-21.mp3 gt2013.08.12-14373-ITEMA_23404867-2013C49904E0044-21.mp3 gt2023.06.29-14373-ITEMA_23440573-2022C49904E0001-21.mp3 gt2023.06.29-14373-ITEMA_23440573-2022C49904E0002-21.mp3 gt2023.06.29-14373-ITEMA_23440573-2022C49904E0003-21.mp3 gt2023.06.29-14373-ITEMA_23440573-2022C49904E0004-21.mp3 gt2023.08.07-14373-ITEMA_23454835-2022C49904E0001-21.mp3 sav
    $ echo "coucou    toi"
    +15:08:19 echo 'coucou    toi'
    coucou    toi
    $ set +x
    +15:08:32 set +x
    $ echo "coucou    toi"
    coucou    toi

  9. #9
    Modérateur
    Avatar de N_BaH
    Profil pro
    Inscrit en
    Février 2008
    Messages
    7 635
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2008
    Messages : 7 635
    Par défaut
    non, je ne suis pas d'accord. La chaîne est : les guillemets ne font pas partie de la chaîne.*
    et donc echo $var est équivalent à , sans guilllemets.

    --
    * s'il l'étaient, ils seraient, de toutes manières, considérés comme de simples caractères, et n'auraient aucunes capacités protectrices des développements du shell.
    .
    N'oubliez pas de consulter les cours shell, la FAQ, et les pages man.

  10. #10
    Expert confirmé
    Homme Profil pro
    Développeur informatique en retraite
    Inscrit en
    Avril 2008
    Messages
    2 102
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Côtes d'Armor (Bretagne)

    Informations professionnelles :
    Activité : Développeur informatique en retraite

    Informations forums :
    Inscription : Avril 2008
    Messages : 2 102
    Par défaut
    Citation Envoyé par N_BaH Voir le message
    echo $var est équivalent à echo coucou toi, sans guilllemets.

    --
    * s'il l'étaient, ils seraient, de toutes manières, considérés comme de simples caractères, et n'auraient aucunes capacités protectrices des développements du shell.
    Pour illustrer ceci:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    $ var='ab"c   d"ef'
    $ echo "$var"
    ab"c   d"ef
    $ echo $var 
    ab"c d"ef
    Au passage, il peut être utile de noter que le comportement du "zsh" est quelque peu différent:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    % var='ab"c   d"ef'  # avec 3 espaces
     
    % echo "$var"
    ab"c   d"ef
     
    % echo $var  
    ab"c   d"ef
     
    % echo $0
    -zsh
    Ça peut être bon à savoir...

+ Répondre à la discussion
Cette discussion est résolue.

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