Je veux savoir comment utiliser deux utilitaires «grep» et «sed» ou autre chose pour remplacer la sous-chaîne. J'expliquerai ce que je veux faire ci-dessous.

Nous avons le fichier 'test.txt' avec la chaîne suivante:

A1 = 'AA1', A2 = 'AA2', A3 = 'AA3', A4 = 'AA4', A5 {ATTR} = 'AA5', A6 = 'mot-clé_A'

Après avoir recherché 'keyword_A' en utilisant grep, je veux remplacer la valeur de A5 par une autre chaîne, par exemple, "NEW".

A1 = 'AA1', A2 = 'AA2', A3 = 'AA3', A4 = 'AA4', A5 {ATTR} = 'NEW', A6 = 'keyword_A'

J'ai essayé d'utiliser deux commandes comme

grep keyword_A test.txt | sed -e 's/blabla/blabla/'

Après avoir essayé tout ce que je sais, j'ai abandonné du tout.

S'il vous plaît laissez-moi savoir la bonne solution.

1
SeungCheol Han 24 janv. 2017 à 07:03

6 réponses

Meilleure réponse

Tout d'abord, vous n'avez jamais besoin de grep et sed. Sed dispose d'un moteur de recherche complet d'expressions régulières, c'est donc un sur-ensemble de grep. Cette commande lira test.txt, modifiera les lignes que vous avez indiquées et imprimera le résultat complet sur la sortie standard:

sed "/keyword_A/s/A5{ATTR}='[A-Z0-9]*'/A5{ATTR}='NEW'/g" < test.txt

Si vous souhaitez stocker les résultats dans le fichier test.txt, utilisez le commutateur -i (modification sur place) sur sed:

sed "/keyword_A/s/A5{ATTR}='[A-Z0-9]*'/A5{ATTR}='NEW'/g" -i.bak test.txt

Si vous souhaitez sélectionner uniquement les lignes indiquées, les modifier et n’imprimer que ces lignes en sortie standard, utilisez une combinaison de la commande p (impression) et de la -n (pas de sortie).

sed "/keyword_A/s/A5{ATTR}='[A-Z0-9]*'/A5{ATTR}='NEW'/gp" -n test.txt
2
Robᵩ 24 janv. 2017 à 04:09
A5="NEW"
A6="keyword_A"

# with sed
sed "s/='[^']*\(',[[:blank:]]*A6='${A6}'\)/='${A5}\1/" YourFile

# with awk
awk -F "'" -v A5="${A5}" -v A6="${A6}" '
   BEGIN { OFS="\047" }
   $12 == A6 { $10 = A5; $0 = $0 }
   7
   ' YourFile
  • Changez à la fin de la chaîne, pour sed et en utilisant ' comme séparateur de champ dans awk au lieu de l'espace traditionnel.
  • en supposant qu'il n'y a pas de ' dans la valeur (ou besoin de traiter la méthode d'échappement) pour la version awk
0
NeronLeVelu 24 janv. 2017 à 12:15

En utilisant quelques variables, vous pouvez définir le mot-clé et le remplacement (s'ils changent du tout):

q="keyword_A"
r="NEW"

Puis avec sed:

sed -r "s/^(.+\{.+\}=')(.+)('.+"${q}".+)$/\1"${r}"\3/" file

Résultat:

A1='AA1', A2='AA2', A3='AA3', A4='AA4', A5{ATTR}='NEW', A6='keyword_A'
0
l'L'l 24 janv. 2017 à 04:32

Nous pouvons simplement remplacer directement la cinquième colonne lorsque le mot-clé sting_A est trouvé comme indiqué ci-dessous:

awk -F, 'BEGIN{OFS=",";}/keyword_A/{$5="A5{ATTR}='"'"NEW"'"'"}1' filename
0
Vicky 29 janv. 2017 à 13:32

Utiliser grep + sed est toujours la mauvaise approche. Voici une façon de le faire avec GNU awk:

$ awk '/keyword_A/{ $0=gensub(/(A5({[^}]+})?=\047)[^\047]+/,"\\1NEW",1) } 1' file
A1='AA1', A2='AA2', A3='AA3', A4='AA4', A5{ATTR}='NEW', A6='keyword_A'
0
Ed Morton 24 janv. 2017 à 04:14

Quelques légères alternatives:

sed -r "/keyword_A/s/(A5[^']*')[^']*/\1NEW/"

awk -F"'" '/keyword_A/{$10 = "NEW"}1' OFS="'"

Bien sûr, le point négatif avec awk est que vous devrez ensuite renommer le nouveau fichier.

0
grail 29 janv. 2017 à 18:41