Comment supprimer un caractère spécifique dans une chaîne, mais uniquement s'il n'y a pas de numéro sur cette ligne sous Linux

8

J'ai été perplexe avec ce problème apparemment simple à résoudre .. enfin, pendant un certain temps.

Voici un exemple de sortie du fichier que je dois modifier:

$cat file
George Washington
Geneva Convention
123,281,029 USD
342,019,929 EUR

Je dois supprimer les espaces entre "George Washington" et "Convention de Genève", mais pas les espaces entre "123 281 029 USD" ou "342 019 929 EUR".

Essentiellement, mon objectif ici est de supprimer uniquement l'espace entre les mots d'une ligne s'il n'y a pas de chiffres sur cette ligne.

J'ai essayé d'éditer le fichier via grep -v [0-9] $file | sed 's/ //', mais la seule façon de fonctionner est de produire un autre fichier, mais cela signifierait exclure toutes les lignes avec des numéros de l'ancien fichier vers le nouveau fichier, ce qui n'est pas ce dont j'ai besoin ..

J'ai essayé des boucles assez ridicules avec grep et sedmais rien ne semble fonctionner correctement.

Encore une fois, voici l'exemple de sortie du fichier:

$cat file
George Washington
Geneva Convention
123,281,029 USD
342,019,929 EUR

Voici ma sortie souhaitée:

$cat file
GeorgeWashington
GenevaConvention
123,281,029 USD
342,019,929 EUR
user62129
la source

Réponses:

15

En utilisant sed:

sed '/[0-9]/!s/ //g' filename

Cela supprimerait les espaces sur toutes les lignes qui ne contiennent pas de chiffre.

En utilisant awk:

awk '!/[0-9]/{gsub(" ", "", $0)};1' filename

Pour supprimer l'espace uniquement entre les deux premiers mots (en utilisant ici GNU sedpour -r, utilisez -Eplutôt sur BSD):

sed -r '/[0-9]/!s/([^ ]+) ([^ ]+)/\1\2/' filename
devnull
la source
Parfait! Ceci est exactement ce que je cherchais! Impossible de trouver la syntaxe n'importe où pour la partie "/ [0-9] /! S /". Merci beaucoup.
user62129
@ user62129 - si cette réponse résout votre problème, veuillez prendre une minute et cocher la coche sous le décompte des votes à gauche, cela signifiera à tout le monde que votre problème a été résolu.
slm
7

En utilisant perl:

perl -ple 's/\s+//g unless /\d/' file
cuonglm
la source
4

Pour une approche plus générale, supprimez uniquement les espaces situés entre deux lettres. De cette façon, cela peut fonctionner même si les lignes ont des chiffres, il ignore simplement les espaces autour des chiffres:

perl -pe 's/([a-z])\s+([a-z])/$1$2/ig' file

Cette volonté, par exemple, tourner George and Harry 12 EURà GerogeandHArry 12 EURet toujours fonctionner correctement pour les cas dans votre exemple.

terdon
la source