Commande sed

Résolu/Fermé
mo3sam
Messages postés
3
Date d'inscription
jeudi 26 mai 2011
Statut
Membre
Dernière intervention
27 mai 2011
- 26 mai 2011 à 20:33
mo3sam
Messages postés
3
Date d'inscription
jeudi 26 mai 2011
Statut
Membre
Dernière intervention
27 mai 2011
- 27 mai 2011 à 13:02
Bonjour a tous,

je viens vous comme dernier recours :s :s
quelqu'un peut t-il m'expliquer en francais comment fonctionne cette commande etape par etape svp , je n'arrive pas à comprendre comment son fonctionnement meme si j'ai le resultat sevant moi ! :

 echo Abcdef | sed 's/\(.*\)\(b.*\)\(e.*\)/\2\1\3/' 


le resultat de cette commande est bcdAef

Pas besoin d'expliquer echo c'est la commande sed qui me pose probleme !!

merci a vous .



6 réponses

lami20j
Messages postés
21331
Date d'inscription
jeudi 4 novembre 2004
Statut
Modérateur, Contributeur sécurité
Dernière intervention
30 octobre 2019
3 565
Modifié par lami20j le 26/05/2011 à 20:46
Salut,

Les parenthèses ont le rôle de capturer le motif trouvé - sont numérotées en commençant de gauche chaque parenthèse ouvrante
Elles sont avec un backslash à cause de leur interprétation du shell
\1, \2 et \3 représentent ce que les parenthèses ont capturé (on peut les inverser en fonction de résultat desiré)
. - c'est n'importe quel caractère
* - c'est un quantificateur (reconnaît zéro, une ou n'importe combien de fois le métacaractère/caractère précédent

Voici la commande exécutée pour chaque capture pour mieux voir ce qui se passe

@debian-acer:~$ echo Abcdef | sed 's/\(.*\)\(b.*\)\(e.*\)/\2\1\3/'    
bcdAef   
@debian-acer:~$ echo Abcdef | sed 's/\(.*\)\(b.*\)\(e.*\)/\2/'    
bcd   
@debian-acer:~$ echo Abcdef | sed 's/\(.*\)\(b.*\)\(e.*\)/\1/'    
A   
@debian-acer:~$ echo Abcdef | sed 's/\(.*\)\(b.*\)\(e.*\)/\3/'    
ef


GNU/Linux:Linux is Not Ubuntu! Quel linux choisir ne veut pas dire votre Distribution préférée,
106485010510997108
2
Brazhak
Messages postés
40
Date d'inscription
mercredi 18 juillet 2007
Statut
Membre
Dernière intervention
7 juin 2011
3
27 mai 2011 à 09:40
Bonjour,

Alors, si on reprend ta commande :

echo Abcdef | sed 's/\(.*\)\(b.*\)\(e.*\)/\2\1\3/'

Ce qu'il faut savoir, c'est que tous les \ (anti-slashes) servent à protéger le caractère suivant. Autrement dit ici les parenthèses ( ) et les références arrières 2 1 3
Si tu veux bien, pour plus de visibilité, nous allons retirer volontairement ces anti-slashes. L'expression sed va donc ressembler à cela :

sed 's/(.*)(b.*)(e.*)/213/'

Le contenu des parenthèses est appelé "sous-expression". Pour information, tu peux en avoir au maximum 9 dans une commande sed. Là, tu en as 3.

La première (.*), indique que tu vas prendre n'importe quel caractère - le . - autant de fois qu'il apparait - la caractère * -

La seconde (b.*), indique de la même manière que tu vas prendre n'importe quel caractère - le . - autant de fois qu'il apparait - la caractère * - MAIS commençant par la lettre b

Pour l'instant tu as donc :
expr 1 : A
expr 2 : bcdef

Idem pour la dernière sous-expression sauf qu'elle doit commencer par un e.
Donc :
expr 1 : A
expr 2 : bcd
expr 3 : ef


Enfin, tu vas faire appel à ces sous-expression dans l'ordre où tu les as définis, d'où le 2 1 3.

J'espère avoir pu t'éclaircir...
2
lami20j
Messages postés
21331
Date d'inscription
jeudi 4 novembre 2004
Statut
Modérateur, Contributeur sécurité
Dernière intervention
30 octobre 2019
3 565
Modifié par lami20j le 27/05/2011 à 10:21
Salut,

Ce qu'il faut savoir, c'est que tous les \ (anti-slashes) servent à protéger le caractère suivant.
Sauf dans la partie remplacement.

Si on a l'option -r pour la commande on n'est pas obligé d'utiliser les backslashs, comme ça on peut aussi remarqué que les backslash dans la partie MOTIF n'ont pas le même rôle que dans la partie REMPLACEMENT

$ echo Abcdef | sed -r 's/(.*)(b.*)(e.*)/\2\1\3/'  
bcdAef


Une expression, sous-expression n'est pas vraiment adapté pour le langage des regex. On utilises plutôt MOTIF.
En revanche on peu utiliser des expressions dans la partie remplacement, par exemple dans perl avec le modificateur e
$ echo 2 4| perl -pe 's/(.) (.)/$1+$2/e' 
6


Edit : Mea culpa, je viens de reprendre mon livre préféré et le sous-expression fait parti des termes abordés. Désolé.
0
lami20j
Messages postés
21331
Date d'inscription
jeudi 4 novembre 2004
Statut
Modérateur, Contributeur sécurité
Dernière intervention
30 octobre 2019
3 565
27 mai 2011 à 10:29
Salut,

Avant de t'es lancer dans l'utilisation des regex, bien sûr il faut les apprendre.
Les regex c'est un mini langage qui te permet de chercher des mots, phrases, dates, etc. dans un texte en utilisant des motifs crées avec ce mini langage.

Ensuite il y a les applications et des langages de programmation qui utilisent ce mini langage chacun un peu à sa manière.
Parmi les applications qui utilisent les regex : grep, sed, awk, perl, etc.
Parmi les langages : php, python, perl, awk, C, C++, VB.NET, java

A savoir qu'il y a aussi des éditeurs de texte qui utilisent les regex : Vim, Emacs, Scite, etc

Ensuite il y a les moteurs qui exécutent les regex.

Voici un très bon livre, en plus elle est dispo en pdf
https://docstore.mik.ua/orelly/perl4/mre/mre.pdf



echo aabbabbaab | sed 's/[ab]*/x/'

==> substitue a ou b une ou plusieurs fois par x

ce qui donne bien sur a la fin tout simplement

x


merci pour ta patience


Dans ce cas il s'agit d'une classe de caractères [ab] qui peut reconnaître soit a soit b mais pas ab.
Lorsqu'on mets [ab]* c'est un peu comme on mettais .* avec la condition que . reconnaît seulement a ou b.
En français ça donne quelque chose de genre : quelque soit a ou b, si on le trouve alors on le reconnaît zéro fois, une fois où n'importe combien de fois (c'est * qui quantifie).
Mais pourquoi un seul x et pas plusieurs?
Puisqueu * c'est un quantificateur gourmand qui va avaler tout donc il va remplacer tout par x.

Je ne connais pas les syntaxe ou les limites de sed concernant la gourmandise mais voici le même exemple avec perl.

lami20j@debian-acer:/mnt/sda7$ echo aabbabbaab | perl -pe 's/[ab]*/x/'
x
lami20j@debian-acer:/mnt/sda7$ echo aabbabbaab | perl -pe 's/[ab]*?/x/'
xaabbabbaab

*? permet de limiter la gourmandise de *
On voit que cette fois x remplace seulement le 1er caractère


et au fait que capturent les parentheses exactement a chaque fois ?

Les parenthèses capturent ce qu'on leur demande (Brazhak t'a expliquer dans ce message, moi j'ai divisé la commande en 3 pour voir ce qu'on capture)

et aussi pq y a t il un
Merci d'éviter les abréviation et/ou SMS.

veut dire n'importe quel caractere ??? !!!
Ca veut dire tout caractère imprimable ou pas.

Voici quelques liens
https://openclassrooms.com/fr/courses/918836-concevez-votre-site-web-avec-php-et-mysql/916990-les-expressions-regulieres-partie-1-2
https://openclassrooms.com/fr/courses/918836-concevez-votre-site-web-avec-php-et-mysql/917386-les-expressions-regulieres-partie-2-2
https://openclassrooms.com/fr/courses/918836-concevez-votre-site-web-avec-php-et-mysql/918834-memento-des-expressions-regulieres
http://perl.mines-albi.fr/DocFr/perlreref.html
http://perl.mines-albi.fr/DocFr/perlrequick.html
https://lumadis.be/regex/tuto_pcre.php

Dans les liens que je t'ai donné concentre toi sur les regex et les explications et pas sur l'application où le langage que tu veux utiliser.
A savoir que chaque application/langage utilise les regex un peu à leur façon donc une regex peut fonctionner ou pas en fonction d'application ou du langage
1
zipe31
Messages postés
36324
Date d'inscription
dimanche 7 novembre 2010
Statut
Contributeur
Dernière intervention
27 janvier 2021
6 586
27 mai 2011 à 10:55
Salut,

Je ne connais pas les syntaxe ou les limites de sed concernant la gourmandise mais voici le même exemple avec perl.

lami20j@debian-acer:/mnt/sda7$ echo aabbabbaab | perl -pe 's/[ab]*?/x/'
xaabbabbaab


Avec sed ça donne :

$ echo aabbabbaab | sed 's/[^ab]*/x/'
xaabbabbaab

;-))
0
lami20j
Messages postés
21331
Date d'inscription
jeudi 4 novembre 2004
Statut
Modérateur, Contributeur sécurité
Dernière intervention
30 octobre 2019
3 565
Modifié par lami20j le 27/05/2011 à 11:22
Salut,

En fait tu viens de me montrer une erreur.
*? ou [^ab]* remplace rien avec un x ce qui veut dire que la chaîne n'est pas modifié mais qu'on ajoute un x au début de la chaine.
Ce que je voulais montrer c'est le remplacement seulement du 1er caractère au début de la chaine et pas d'une assertion nulle
En ce cas on est obligé de forcer le moteur à reconnaître au moins une fois, donc je vais utiliser le quantificateur non-gourmand +?

A vrai dire ce n'est que pour montrer un exemple puisqu'en ce cas il suffit de remplacer le 1er caractère de la chaine. ;-) et pas se casser la tête avec les quantificateurs.

lami20j@debian-acer:/mnt/sda7$ echo aabbabbaab  
aabbabbaab 
lami20j@debian-acer:$ echo aabbabbaab | wc -c 
11 
lami20j@debian-acer:$ echo aabbabbaab | perl -pe 's/[ab]*?/x/' 
xaabbabbaab 
lami20j@debian-acer:$ echo aabbabbaab | perl -pe 's/[ab]*?/x/'|wc -c 
12 
lami20j@debian-acer:$ echo aabbabbaab | sed 's/[^ab]*/x/' 
xaabbabbaab 
lami20j@debian-acer:$ echo aabbabbaab | sed 's/[^ab]*/x/'|wc -c 
12 
lami20j@debian-acer:$ echo aabbabbaab | perl -pe 's/[ab]+?/x/' 
xabbabbaab 
lami20j@debian-acer:$ echo aabbabbaab | perl -pe 's/[ab]+?/x/'|wc -c 
11
0
mo3sam
Messages postés
3
Date d'inscription
jeudi 26 mai 2011
Statut
Membre
Dernière intervention
27 mai 2011

Modifié par mo3sam le 26/05/2011 à 21:29
je suis désolé mais je n'ai toujours pas compris et c'est surement de ma faute mais peux tu m'expliquer ce que fait la commande etape par etape stp un peu de cette facon par exemple :

   echo aabbabbaab | sed 's/[ab]*/x/'
==> substitue a ou b une ou plusieurs fois par x

ce qui donne bien sur a la fin tout simplement
  x

merci pour ta patience

et au fait que capturent les parentheses exactement a chaque fois ?
et aussi pq y a t il un
 .
apres le b et le e alors que le
 .
veut dire n'importe quel caractere ??? !!!

j t assure ca m rend dingue :)
merci encore
0

Vous n’avez pas trouvé la réponse que vous recherchez ?

Posez votre question
zipe31
Messages postés
36324
Date d'inscription
dimanche 7 novembre 2010
Statut
Contributeur
Dernière intervention
27 janvier 2021
6 586
27 mai 2011 à 10:23
Salut,

Voir dans la FAQ : Les sous-expressions et références arrières ;-))
0
mo3sam
Messages postés
3
Date d'inscription
jeudi 26 mai 2011
Statut
Membre
Dernière intervention
27 mai 2011

27 mai 2011 à 13:02
magnifique les gars :))

merci a tous
0