#1 Le 29/08/2017, à 14:19
- Beuhlet_Reseau
Awk avec multiple sed non optimisé
Hello,
Je souhait juste un avis sur une commande un peu fumée. Merci à Watel et le Pingouin pour leur aide précédente.
Pour rappel, je souhaitais sur un champ particulier ne récupérer que la première chaine de caractère, qui pouvait alors être séparé soit par un espace " ", un "," ou alors un ":". Leur sublime commande me permettait de récupérer cette première chaine de caractère en prenant en compte ce genre de souci.
Maintenant je dirais que 95% de mon fichier est ok grâce à eux.
Juste pour rappel, la commande venu d'ailleurs :
awk 'BEGIN{FS=OFS="|"}{if($6){split($6,ar,"[ :,]"); $6=ar[1]}}1'
Elle test si le champ 6 est non vide, et le split dans la variable ar en prenant en compte la regex [ :,], enfin la variable 6 prend la valeur de ar 1 fois. (je crois aha)
Pour simplifier que lorsque la première chaîne récupérée est égale à Bonjour ou Cher, ou Votre de les remplacer par le terme Premise. Et lorsque que la chaîne récupérée est égale à Bye de le remplacer par Disable. Voici comme je m'y prend :
more fichier2test | sed '/^$/d;/SP268/d;/row/d' | awk 'BEGIN{FS=OFS="|"}{if($6){split($6,ar,"[ :,]"); $6=ar[1]}}1' | sed 's/Bonjour/Premise/;s/Cher/Premise/;s/Votre/Premise/;s/Bye/Disable/'
En gros, sur mon fichier en entrée, je delete les lignes vides, les lignes contenant SP268 ainsi que les lignes contenant row.
Ensuite grosse commande de forain pour ne récupérer que la première chaîne de caractère du champs n°6 avec la regex "[ :,]" pour prendre en compte les cas où le champs est foireux pour changer.
Enfin, à la zoulou, je fais tout bêtement un sed 1,2,3,4 fois :lol:
Je post seulement ce message pour savoir si il est optimisable, sinon ça roule plutôt pas mal aha.
Dernière modification par Beuhlet_Reseau (Le 29/08/2017, à 14:21)
L'avenir appartient à ceux qui se lèvent tôt... Pas ceux qui crachent trop (vite?).
Hors ligne
#2 Le 29/08/2017, à 15:11
- Watael
Re : Awk avec multiple sed non optimisé
mais NON ! awk est un langage complet qui se suffit à lui-même !
d'abord, sed sait lire les fichiers sans aide extérieure;
donc more est inutile.
on revient sur awk :
- il peut très bien ne traiter que les lignes qui ne correspondent pas à un motif donné (les trois suppressions de sed peuvent faire l'objet d'une seule regex).
- il peut faire des substitutions, sur une ligne entière également.
awk est un langage complet qui se suffit à lui-même !
Connected \o/
Welcome to sHell. · eval is evil.
Hors ligne
#3 Le 29/08/2017, à 15:47
- Beuhlet_Reseau
Re : Awk avec multiple sed non optimisé
Excuse moi Watael pour la faute dans ton prénom de mon premier post je sais que cela ta quelque peu remonté
Je sais bien mais le souci est que je n'arrive pas à enchainer les commandes sous AWK grr
Voici ma commande dans son intégralité, et elle ne fonctionne pas terrible (sauf on l'on prend bout par bout la commande) grrr :
sed '/^$/d;/SP268/d;/row/d'| awk 'BEGIN{FS=OFS="|"}{if($6){split($6,ar,"[ :,]"); $6=ar[1]}}1 ; {gsub("^0+","",$3);{if($4)$4=int($4)} }1' | sed 's/Bonjour/Premise/;s/Cher/Premise/;s/Votre/Premise/;s/Bye/Disable/' MONFICHIER2TEST
D'une elle pique les yeux.
De deux, elle ne fonctionne que 1 ligne sur 2.
EDIT : En enlevant le point virgule ";" avant le gsub il fonctionne sur toutes les lignes mais la conversion en integer derrière non.
Bon reprenons, j'ai tenté ceci Watael et c'est KO (évidemment la précédente l'étais donc bon ...):
sed '/^$/d;/SP268/d;/row/d'| awk 'BEGIN{FS=OFS="|"}{if($6){split($6,ar,"[ :,]"); $6=ar[1]}}1 ; {gsub("^0+","",$3)("^Bonjour","Premise",$6)("^Cher","Premise",$6)("^Votre","Premise",$6);{if($4)$4=int($4)} }1'
L'avenir appartient à ceux qui se lèvent tôt... Pas ceux qui crachent trop (vite?).
Hors ligne
#4 Le 29/08/2017, à 17:04
- Watael
Re : Awk avec multiple sed non optimisé
Excuse moi Watael pour la faute dans ton prénom de mon premier post je sais que cela ta quelque peu remonté roll
je n'avais pas vu.
maintenant, je suis en colère !!!
maintenant, forcément, si tu mets le guidon à la place de la tige de selle, tu vas avoir mal : il faut un gsub() par remplacement à effectuer.
awk 'BEGIN{FS=OFS="|"}
! /^$|SP268|row/{
if($4)$4=int($4)
if($6){
split($6,ar,"[ :,]");
$6=ar[1]
};
gsub("^0+","",$3);
gsub("^(Bonjour|Cher|Votre)","Premise",$6);
}1' fichier
il faudrait remettre un bout du fichier original qu'on fasse éventuellement des tests.
Dernière modification par Watael (Le 29/08/2017, à 17:06)
Connected \o/
Welcome to sHell. · eval is evil.
Hors ligne
#5 Le 30/08/2017, à 09:59
- Beuhlet_Reseau
Re : Awk avec multiple sed non optimisé
Merci énormément Watael,
Je modifie un peu ta commande pour coller avec ce cas (j'ai tronqué des informations pour éviter l'effet pâté) :
awk 'BEGIN{FS=OFS="|"}
! /^$|SP268|row/{
if($2)$2=int($2)
if($4){
split($4,ar,"[ :,]");
$4=ar[1]
};
gsub("^0+","",$1);
gsub("^(Bonjour|Cher|Votre)","Premise",$4);
}1' fichier
Voici quelques exemples choisis avec soin reprenant tous les cas possibles !
Nbrz Percent Status Message
00039301207 92,452 4 Bye: ##Error,45
00033116625 100 1 Votre : ##Error1
00087740674 100 1 Info : ##Error,45
00051554002 80 1 Hello, ##Error,1
00028970537 82,451 1 Chir ##Error,1
Le résultat voulu étant :
Nbrz Percent Status Message
39301207 92 4 Disable
33116625 100 1 Premise
87740674 100 1 Info
51554002 80 1 Premise
28970537 82 1 Premise
Je vais tenter quelques choses
En gros si, la valeur de $2 est comprise en 81 et 99 je la ramène à 80. Ca a l'air très simple ! :
if($2 >= 81 && $2 <= 99){
$2=80
};
=> Ca passe
RETOUR : La commande est bonne, mais elle n'a pas l'aire de supprimer les infos que l''on voulait (! /^$|SP268|row/)
Dernière modification par Beuhlet_Reseau (Le 30/08/2017, à 11:28)
L'avenir appartient à ceux qui se lèvent tôt... Pas ceux qui crachent trop (vite?).
Hors ligne
#6 Le 30/08/2017, à 11:47
- Watael
Re : Awk avec multiple sed non optimisé
$ echo "
milka
SP268
suchard
poulain
tra la la row bla bla bla
" | awk '! /^$|SP268|row/'
milka
suchard
poulain
Connected \o/
Welcome to sHell. · eval is evil.
Hors ligne
#7 Le 30/08/2017, à 12:51
- Beuhlet_Reseau
Re : Awk avec multiple sed non optimisé
Oui tout à fait d'accord, je remarque que la problématique est surement dû à l'enchaînement de commandes derrière. Mais bon après tout on va pas faire les difficiles !
Merci encore Watael !
L'avenir appartient à ceux qui se lèvent tôt... Pas ceux qui crachent trop (vite?).
Hors ligne
#8 Le 30/08/2017, à 13:17
- Watael
Re : Awk avec multiple sed non optimisé
les traitements entre les accolades, qui suivent immédiatement le motif recherché, sont conditionnés par la (non-)correspondance au motif indiqué.
c'est ainsi que fonctionne awk : « An AWK program consists of a sequence of pattern-action statements [...] ».
/motif/ { traitement pour les lignes incluant motif }
si aucun motif n'est indiqué, le traitement est appliqué à toutes les lignes
/motif/ { traitement pour les lignes incluant motif } ; { traitement pour toutes les lignes }
Dernière modification par Watael (Le 30/08/2017, à 13:18)
Connected \o/
Welcome to sHell. · eval is evil.
Hors ligne