Réponses:
Vous pouvez utiliser sed
:
sed -i 's/^/your_string /' your_file
Grâce aux commentaires de Stéphane et Marco, notez que l' -i
option n'est pas POSIX. Une façon POSIX de faire ce qui précède serait
sed 's/^/your_string /' your_file > tmp_copy && mv tmp_copy your_file
ou perl
:
perl -pi -e 's/^/your_string /' your_file
Explication
Les deux commandes effectuent une substitution d'expression régulière, remplaçant le début d'une ligne ( ^
) par la chaîne souhaitée. Le -i
commutateur dans les deux commandes s'assure que le fichier est édité sur place (c'est-à-dire que les changements sont reflétés dans le fichier au lieu d'être imprimés sur stdout).
sed
devrait être disponible sur tout système d'exploitation compatible POSIX et perl
devrait être disponible sur la plupart des Unices modernes, à l'exception peut-être de ceux qui ont fait l'effort de le supprimer.
sed -i
n'est pas POSIX. C'est GNU. FreeBSD sed
a une option similaire, mais vous en avez besoin sed -i ''
.
-i
crée une copie temporaire (c'est pourquoi j'ai dit que les changements sont reflétés dans le fichier d'origine); Je voulais dire que vous obtenez la même sémantique que la substitution sur place. Veuillez vérifier que la réponse mise à jour est conforme à POSIX.
$$
(l'ID de processus du shell actuel) dans le cadre d'un nom de fichier temporaire; cela évite l'effort de penser à un nom unique garanti à chaque fois:command filename > filename.$$ && mv filename.$$ filename
:|paste -d'foo ' - - - - input > output
(je plaisante, mais vous trouverez probablement que c'est la plus rapide de toutes les solutions publiées ici: -b).
La voie canonique est:
sed 's/^/foo /' < input > output
Cependant, il n'est pas facilement adapté aux chaînes arbitraires. Par exemple,
sed "s/^/$var /"
Ne fonctionne que si $var
ne contient pas, &
, \
, /
ni les caractères de nouvelle ligne.
À cet égard,
export var
awk '{print ENVIRON["var"], $0}'
ou
perl -pe '$_="$ENV{var} $_"'
fonctionnerait mieux.
Je présente une solution utilisant le awk
préfixe de la chaîne "foo".
awk '{ print "foo", $0; }' input > output
awk
est multiplateforme et disponible sur n'importe quel système POSIX. Il ne fait pas de modification sur place. Si vous souhaitez éditer un fichier sans en créer un second, vous devrez utiliser un fichier temporaire. Voir la sed
réponse de Joseph , elle montre la syntaxe. Un autre hack consiste à utiliser la syntaxe suivante, qui consiste essentiellement à créer un fichier temporaire avec le même nom de fichier que le fichier d'origine.
{ rm file; awk '{ print "foo", $0 }' > file; } < file
reducto# wc -l foo
`914 foo` reducto# { rm foo ; awk '{ print "prepend" , $0 }' > foo } < foo
>
Cela ne semble pas fonctionner. J'essayais car la redirection vers l'original me rendait nerveux, mais ça ne démarre même pas.
Vous pouvez éviter les problèmes de modification sur place avec les outils de flux en utilisant un outil qui effectue normalement la modification sur place - un éditeur!
ex sample.txt -c "%s/^/foo /" -c wq
Il y a un avantage supplémentaire: les commandes sont faciles et évidentes pour quiconque est familiarisé avec le seul véritable éditeur.
Vous pouvez utiliser perl
pour ce faire:
$ perl -pi -e 's/^/mystring /' afile.txt
Créez un exemple de fichier.
$ seq 5 > afile.txt
$ cat afile.txt
1
2
3
4
5
Exécutez la commande ci-dessus:
$ perl -pi -e 's/^/mystring /' afile.txt
$ cat afile.txt
mystring 1
mystring 2
mystring 3
mystring 4
mystring 5
sed
, j'ai montré comment utiliser Perl .... ne cherchant pas une guerre sainte en la matière.
Utiliser simplement Bash
while IFS= read -r line; do echo "foo" "${line}" ; done < input > Output
Utiliser Python
python -c "import sys; print 'foo '.join([ l for l in sys.stdin.readlines() ])" < input > Output
Si vous souhaitez éditer sur place
import fileinput
import sys
for line in fileinput.input(['inputfile'], inplace=True):
sys.stdout.write('foo {l}'.format(l=line))
awk
sur de très petits fichiers. Le comportement varie selon les implémentations d'écho, il supprime les blancs de début et de fin et traite les barres obliques inverses spécialement.
prefix () { while IFS= read -r REPLY; do printf "%s%s\n" "$1" "$REPLY"; done; }
devrait être plus correct.
{}
? Je pense que @Matt suggérait que vous en fassiez une fonction nommée, à quoi bon {}
sans nom de fonction?
Ou vous pouvez effectuer les opérations suivantes:
vi filename.txt
Esc(pour vous assurer que vous êtes en NORMAL
mode), puis entrez la commande suivante:
:1,$ s/^/mystring
1,$
simplement %
. Cela rend la commande :%s/^/string/
.
-i
commutateur n'édite pas le fichier en place. Il crée un nouveau fichier et écrase l'original une fois terminé (preuve: l'inode change). Il n'y a pas beaucoup d'outils qui effectuent réellement l'édition sur place, ce qui est une opération dangereuse. De plus, puisque vous mentionnez POSIX, le-i
commutateur n'est pas obligatoire pour un compatible POSIXsed
, c'est une caractéristique de certaines implémentations particulières.