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 :

[Exercices] Liste d'exercices corrigés en shell script et bash


Sujet :

Shell et commandes GNU

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Rédacteur

    Avatar de ok.Idriss
    Homme Profil pro
    IS Consultant
    Inscrit en
    Février 2009
    Messages
    5 220
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : IS Consultant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Février 2009
    Messages : 5 220
    Par défaut [Exercices] Liste d'exercices corrigés en shell script et bash
    Bonjour à tous.

    Je vous présente une nouvelle liste d'exercices corrigés avec un format plus adapté : Exercices shell scripts.

    Cet article regroupe des exercices corrigés en shell scripts Bash et autres langages shell compatibles. Les exercices sont classés par niveaux et peuvent posséder plusieurs solutions.
    N'hésitez pas à laisser vos impressions, et vos propositions de énoncés et solutions en Bash voire même dans un langage shell compatible comme Ksh où autre. Si elles sont jugées pertinentes, elles seront intégrées à l'article. Dans ce cas, merci d'indiquer le niveau correspondant et l'exercice correspondant (on peux rajouter des niveaux au besoin).

    Je remercie déjà tout les participants qui sont mentionnés ici.

    Cordialement,
    Idriss

  2. #2
    Futur Membre du Club
    Profil pro
    Inscrit en
    Juin 2010
    Messages
    5
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2010
    Messages : 5
    Par défaut Exercice 6
    Solution proposée:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    #!/bin/bash
     
    # Prendre tous les arguments et ajouter un saut de ligne pour un tri avec la commande sort
    tab=`echo $* | sed 's/ /\n/g' | sort`
     
    # Afficher le résultat de tout le tableau en supprimant les sauts de lignes précédemment créés
    echo -e "Elements:\n`echo ${tab[*]}|sed 's/\n//g'`"

  3. #3
    Rédacteur

    Avatar de ok.Idriss
    Homme Profil pro
    IS Consultant
    Inscrit en
    Février 2009
    Messages
    5 220
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : IS Consultant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Février 2009
    Messages : 5 220
    Par défaut
    Bonjour jsnooper.

    Merci de ta participation, toutefois cette solution ne répond pas à la contrainte qui est de passer par l'algorithme du tri à bulle (sinon un sort aurait suffit ).

    En effet il existe différentes possibilités pour trier des éléments et la tienne est efficace mais ne répond pas à cette contrainte "pédagogique".

    Toutefois, lorsque j'aurais un peu de temps, ça vaudrait peut être le coup de faire un exercice plus général sur les façons de trier des éléments. Je vous laisse exprimer vos avis dessus et éventuellement proposer d'autres solutions. Qu'en pensez-vous ?

    Encore merci

    Idriss

  4. #4
    Futur Membre du Club
    Profil pro
    Inscrit en
    Juin 2010
    Messages
    5
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2010
    Messages : 5
    Par défaut Votre réponse
    Ok... Désolé de ne pas avoir bien lu l’énoncé !

    @++

  5. #5
    Invité de passage
    Homme Profil pro
    Développeur en systèmes embarqués
    Inscrit en
    Juillet 2012
    Messages
    1
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur en systèmes embarqués

    Informations forums :
    Inscription : Juillet 2012
    Messages : 1
    Par défaut
    Plutôt qu'un
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    cat $fichier | while read line
    do
    ...
    done
    pour la lecture ligne par ligne (exercices pour confirmés)

    Le cat est superflu, préférons :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    while read line
    do
    ...
    done < $fichier

  6. #6
    Expert confirmé Avatar de frp31
    Homme Profil pro
    Ingénieur systèmes et réseaux
    Inscrit en
    Juillet 2006
    Messages
    5 196
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 48
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Ingénieur systèmes et réseaux
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Juillet 2006
    Messages : 5 196
    Par défaut
    Citation Envoyé par Louson Voir le message
    Plutôt qu'un
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    cat $fichier | while read line
    do
    ...
    done
    pour la lecture ligne par ligne (exercices pour confirmés)

    Le cat est superflu, préférons :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    while read line
    do
    ...
    done < $fichier
    j'ajouterai meme que la variable ne sert à rien !!!
    la variable de read est REPLY elle existe déjà et elle est chargée aussi si on utilise une variable personnelle !! bref c'est une perte de temps systeme et de memoire d'en charger 2 plutot qu'une

  7. #7
    Membre Expert Avatar de jabbounet
    Homme Profil pro
    Consultant informatique
    Inscrit en
    Juin 2009
    Messages
    1 909
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49

    Informations professionnelles :
    Activité : Consultant informatique

    Informations forums :
    Inscription : Juin 2009
    Messages : 1 909
    Par défaut
    j'ai parcouru rapidement la liste d'exercice, c'est assez intéressant, par contre je ne vois pas ou est le focus pédagogique...

    je m'explique, quand on prend par exemple le premier exercice:

    Créer un script qui demande à l'utilisateur de saisir une note et qui affiche un message en fonction de cette note :

    "très bien" si la note est entre 16 et 20 ;
    "bien" lorsqu'elle est entre 14 et 16 ;
    "assez bien" si la note est entre 12 et 14 ;
    "moyen" si la note est entre 10 et 12 ;
    "insuffisant" si la note est inférieur à 10.
    quel est le but pédagogique, quel est l'élément du langage mis en valeur par ce type d'exercice?

    ici par exemple ce serait la manipulation des structures de contrôle et plus particulièrement les structure conditionnelle....

    bref je pense que avoir une introduction sur les éléments de langage à manipuler est important pour ce type d'exercice.

    note pour ce premier exercice il est aussi possible d'utiliser select.
    http://homel.vsb.cz/~dvo25/reily/boo...sh/ch05_04.htm

  8. #8
    Membre très actif
    Homme Profil pro
    Étudiant
    Inscrit en
    Juillet 2014
    Messages
    174
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 30
    Localisation : Maroc

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Juillet 2014
    Messages : 174
    Par défaut
    une autre solution exercice test user II-B-1
    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
    #!/bin/bash
    menu()
    {
    echo "1 - Vérifier l'existence d'un utilisateur"
    echo "2 - Connaître le UID d'un utilisateur"
    echo "3 - Quitter"
    read -r choix
    }
    verification()
    {
    read -p "le nom de l'utilisateur= " nom
    grep $nom /etc/passwd > fichtest
    if [ -s fichtest ] ;then
    echo "ce utilisateur existe"
    else
    echo "ce utilisateur n'existe pas"
    fi
    }
    uid()
    {
    read -p "le nom de l'utilisateur= " nom
    cat /etc/passwd | grep $nom > fichtest
    if [ -s fichtest ] ;then
    grep $nom /etc/passwd | cut -d : -f 3
    else
    echo "ce utilisateur n'existe pas"
    fi
    }
    repeat=1
    while [ $repeat -eq 1 ]
    do
    menu
    if [ $choix -eq 3 ];then
    echo "au revoir"
    repeat=2
    fi
    if [ $choix -ne 1 ] && [ $choix -ne 2 ] && [ $choix -ne 3 ] ;then
    echo "erreur de saisie"
    fi
    if [ $choix -eq 1 ] ;then
    verification
    fi
    if [ $choix -eq 2 ] ;then
    uid
    fi
    done

  9. #9
    Membre prolifique
    Avatar de Sve@r
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Février 2006
    Messages
    12 832
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Oise (Picardie)

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

    Informations forums :
    Inscription : Février 2006
    Messages : 12 832
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par MR-SMOOT Voir le message
    une autre solution exercice test user II-B-1
    Code bash : 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
    48
    49
    #!/bin/bash
    menu()
    {
        echo "1 - Vérifier l'existence d'un utilisateur"
        echo "2 - Connaître le UID d'un utilisateur"
        echo "3 - Quitter"
        read -r choix
    }
     
    verification()
    {
        read -p "le nom de l'utilisateur= " nom
        grep $nom /etc/passwd > fichtest
        if [ -s fichtest ] ;then
            echo "ce utilisateur existe"
        else
            echo "ce utilisateur n'existe pas"
        fi
    }
     
    uid()
    {
        read -p "le nom de l'utilisateur= " nom
        cat /etc/passwd | grep $nom > fichtest
        if [ -s fichtest ] ;then
            grep $nom /etc/passwd | cut -d : -f 3
        else
            echo "ce utilisateur n'existe pas"
        fi
    }
     
    repeat=1
    while [ $repeat -eq 1 ]
    do
        menu
        if [ $choix -eq 3 ];then
            echo "au revoir"
            repeat=2
        fi
        if [ $choix -ne 1 ] && [ $choix -ne 2 ] && [ $choix -ne 3 ] ;then
            echo "erreur de saisie"
        fi
        if [ $choix -eq 1 ] ;then
            verification
        fi
        if [ $choix -eq 2 ] ;then
            uid
        fi
    done
    Désolé, je ne valide pas
    1. ta fonction "menu()" remplit une variable "choix" qui sera traitée en dehors de celle-ci. Ta fonction n'est donc pas indépendante (si on modifie la variable, faut aller la rechercher partout dans le reste du code pour la modifier aussi).
    2. ton grep que tu rediriges dans un fichier juste pour vérifier qu'il a bien réussi est horrible. Tu génères une écriture disque juste pour mémoriser une info et le jour où tu lances ton script deux fois en parallèle (hé oui, Unix est multitaches donc faut considérer qu'un script peut tourner sur plusieurs instances en même temps), bonjour la collision. Et puis ensuite, quand le script se termine, tu restes avec ton fichier "fichtest" qui va te polluer tous tes répertoires (il est créé là où tu te trouves). Si au-moins tu avais ne serait-ce que pensé à créer ce fichier dans $HOME/tmp (ou au pire dans /tmp) histoire de pas faire le gros sale qui laisse ses fichiers poubelles un peu partout (et je ne parle pas que de toi mais aussi de tous les utilisateurs qui exécuteront ton script).
      Ce qui m'amène d'ailleurs à me demander ce qui se passera si tu lances le script depuis le dossier /etc (après tout, on est libre de se trouver n'importe où dans la machine non ?). Figure de réthorique car je sais très bien ce qui se passera mais c'est pour que toi tu en prennes conscience.
      De plus, moi j'ai tous mes comptes bancaires dans un fichier que j'ai appelé "fichtest" (j'ai le droit non ?). Je suis content le jour où je le perds parce que j'ai lancé ton script !!!
    3. Dans uid tu fais deux fois le même grep. C'est vrai que mémoriser le premier pour le réutiliser ensuite aurait été trop simple et surtout aurait donné un script beaucoup plus rapide...
    4. A propos de ce grep, justement, tu t'es demandé ce qui se passe si on demande l'uid de l'utilisateur "ro" ? ou "oot" ? ou "home" ? ou juste ":" ?
    5. Et enfin ta façon d'évaluer le choix du menu. Déjà tu fais 3 tests distincts pour vérifier s'il est différent de [1, 2, 3] (tu ne connais pas le connecteur "-a" signifiant "and" ? => [ $choix -ne 1 -a $choix -ne 2 -a $choix -ne 3 ]) mais que se passera-t-il si le script évolue et offre ensuite des choix 4, 5 et 6 ? Bonjour le test qu'il faudra alors écrire (tu aurais pu déjà simplifier en regardant juste choix < 1 ou choix > 3). Et sinon tu ne connais pas le case ???


    Désolé, ta solution, bien que montrant certains efforts, est tout sauf réussie car pas assez réfléchie. A la limite elle pourrait servir pour montrer ce qu'il ne faut pas faire...
    Mon Tutoriel sur la programmation «Python»
    Mon Tutoriel sur la programmation «Shell»
    Sinon il y en a pleins d'autres. N'oubliez pas non plus les différentes faq disponibles sur ce site
    Et on poste ses codes entre balises [code] et [/code]

  10. #10
    Membre très actif
    Homme Profil pro
    Étudiant
    Inscrit en
    Juillet 2014
    Messages
    174
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 30
    Localisation : Maroc

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Juillet 2014
    Messages : 174
    Par défaut
    Citation Envoyé par Sve@r Voir le message
    [/LIST]
    Désolé, ta solution (pondue par un admin système en plus ) est tout sauf réussie. A la limite elle pourrait servir pour montrer ce qu'il ne faut pas faire...
    (y) t'a vraiment raison merci pour t'es conseil je vais les prendre en compte
    ps: je suis juste un etudiant au 1ere annee au reseau informatique j'ai actualisé mes info et je ne suis pas un administrateur j'etudie que ccna ,windows server et un peu linux
    donc je pense que mon resultat pour un debutant n'est pas mal parce que le programme marche a la fin ^^ et merci beaucoup pour ton aide

  11. #11
    Membre très actif
    Homme Profil pro
    Étudiant
    Inscrit en
    Juillet 2014
    Messages
    174
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 30
    Localisation : Maroc

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Juillet 2014
    Messages : 174
    Par défaut
    bon voila j'ai fais ce que tu m'avais dit et voila le résultat ^^ j’espère que cette fois y'a pas trop de problème avec le script
    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
    #!/bin/bash
    verification()
    {
    read -p "le nom de l'utilisateur= " nom
    grep "^$nom:" /etc/passwd > /tmp/fichtest
    if [ -s /tmp/fichtest ] ;then
    echo "ce utilisateur existe"
    else
    echo "ce utilisateur n'existe pas"
    fi
    }
    uid()
    {
    read -p "le nom de l'utilisateur= " nom
    grepcut=`grep "^$nom:" /etc/passwd | cut -d : -f 3`
    if [ $grepcut -gt 0 ] ;then
    echo "le uid de $nom est $grepcut "
    else
    echo "ce utilisateur n'existe pas"
    fi
    }
    repeat=1
    while [ $repeat -eq 1 ]
    do
    echo "1 - Verifier l'existence d'un utilisateur"
    echo "2 - Connaitre le UID d'un utilisateur"
    echo "3 - Quitter"
    read -r choix
    if [ $choix -eq 3 ];then
    echo "au revoir"
    repeat=2
    fi
    if [ $choix -lt 1 -o $choix -gt 3 ] ;then
    echo "erreur de saisie"
    fi
    if [ $choix -eq 1 ] ;then
    verification
    fi
    if [ $choix -eq 2 ] ;then
    uid
    fi
    done

  12. #12
    Membre prolifique
    Avatar de Sve@r
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Février 2006
    Messages
    12 832
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Oise (Picardie)

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

    Informations forums :
    Inscription : Février 2006
    Messages : 12 832
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par MR-SMOOT Voir le message
    j'espere que cette fois y'a pas trop de probleme avec le script
    Il y en a un peu moins... mais j'apprécie les efforts. Surtout d'avoir pensé au "^$nom:" dans le grep pour éviter les cas "ro", "oot" et etc. Mais pourquoi avoir enlevé le menu ? Ce n'est pas parce qu'il était mal fait que ce n'était pas une bonne idée...

    Bon, je ne vais pas détailler les soucis résiduels. Juste que créer un fichier (même temporaire) pour mémoriser une simple info...

    Voici ce que je te propose

    Code bash : 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
    48
    #!/bin/bash
    menu()
    {
        echo "1 - Vérifier l'existence d'un utilisateur"
        echo "2 - Connaître le UID d'un utilisateur"
        echo "3 - Quitter"
        read -r choix
        return $choix
    }
     
    verification()
    {
        read -p "le nom de l'utilisateur= " nom
        if grep "^$nom:" /etc/passwd 1>/dev/null; then
            echo "l'utilisateur $nom existe"
            return 0
        else
            echo "l'utilisateur $nom n'existe pas"
            return 1
        fi
    }
     
    uid()
    {
        read -p "le nom de l'utilisateur= " nom
        info=`grep "^$nom:" /etc/passwd`
        if [ -n "$info" ] ;then
            echo "L'utlisateur $nom a comme uid `echo "$info" | cut -d: -f3`"
            return 0
        else
            echo "L'utilisateur $nom n'existe pas"
            return 1
        fi
    }
     
    while true
    do
        menu; choix=$?
        case $choix in
            1) verification;;
            2) uid;;
            3)
                echo "Au revoir"
                break
                ;;
            *) echo "erreur de saisie"
        esac
    done

    C'est pas parfait parfait (fait à la "va-vite" avec beaucoup de code redondant) mais au-moins ça n'a aucun des défauts que j'avais mentionné dans mon post précédent. Les return des fonctions verif() et uid() ne sont pas nécessaires mais j'aime bien que mes fonctions soient booléennes.

    Concernant les fichiers temporaires, déjà faut éviter si possible mais si ça ne l'est pas, c'est alors bien d'adjoindre la variable "$$" (n° pid) dans leurs noms. Ca évite le problème des collisions lors des scripts lancés plusieurs fois en parallèle...
    Mon Tutoriel sur la programmation «Python»
    Mon Tutoriel sur la programmation «Shell»
    Sinon il y en a pleins d'autres. N'oubliez pas non plus les différentes faq disponibles sur ce site
    Et on poste ses codes entre balises [code] et [/code]

Discussions similaires

  1. Exercice liste liée
    Par Isendar dans le forum Algorithmes et structures de données
    Réponses: 7
    Dernier message: 30/05/2008, 07h50
  2. Liste chaînée , exercice simple et perte d'élément
    Par Alternative451 dans le forum C
    Réponses: 1
    Dernier message: 21/04/2008, 15h07
  3. Probleme exercice list
    Par Gebudi. dans le forum C++
    Réponses: 6
    Dernier message: 31/07/2006, 15h43

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