Ganti string dengan konten file menggunakan sed


23

Saya punya dua file berbeda:

File1

/home/user1/  
/home/user2/bin  
/home/user1/a/b/c

File2

<TEXT1>
<TEXT2>

Saya ingin mengganti <TEXT1>dari File2 dengan isi File1 menggunakan sed. Saya mencoba perintah ini, tetapi tidak mendapatkan output yang tepat:

cat File2|sed "s/<TEXT1>/$(cat File1|sed 's/\//\\\//g'|sed 's/$/\\n/g'|tr -d "\n")/g"

Anda dapat menggunakan alat lain juga untuk menyelesaikan masalah ini.


Harap tempel pesan kesalahan itu sehingga kami dapat menemukan sumbernya. Beri tahu kami sedimplementasi mana yang Anda gunakan. Kode Anda berfungsi untuk saya dengan GNU sed.
manatwork

Maaf, tidak mendapatkan kesalahan. Saya tidak mendapatkan hasil yang diinginkan. Outputnya seperti /home/user1/ n/home/user2/bin n/home/user1/a/b/cn <TEXT2>. Tidak mendapat baris baru.
chanchal1987

Tidak yakin apakah ini akan berlaku dalam kasus spesifik Anda, tetapi dengan diffdan patchalat memungkinkan untuk mengganti beberapa baris dalam file dengan baris lain dengan cukup mudah.
Stéphane Gimenez

1
Btw, menggunakan data acak yang dikumpulkan dengan $()skrip sed membuat mata saya berdarah. Jangan pernah menggunakan data eksternal di tempat-tempat di mana beberapa karakter ditafsirkan dengan makna khusus.
Stéphane Gimenez

Jawaban:


24

Inilah solusi skrip sed (lebih mudah dilihat daripada mencoba membuatnya menjadi satu baris pada baris perintah):

/<TEXT1>/ {
  r File1
  d
}

Menjalankannya:

$ sed -f script.sed File2
/home/user1/
/home/user2/bin
/home/user1/a/b/c
<TEXT2>

Terima kasih ini berfungsi. Tetapi saya tidak ingin menggunakan file skrip lainnya. Apakah ada solusi sebaris?
chanchal1987

Tentu:, di sed '/<TEXT1>/{rFile1^Md^M}' File2mana "^ M" Anda menekan kembali. Masalahnya adalah sed benar-benar membutuhkan baris baru di dalam {...} untuk membatasi perintah r dan d.
Kusalananda

6
dengan bash, string gaya posix sedikit lebih bersih:sed $'/<TEXT1>/ {r File1\n d}'
glenn jackman

9
Juga dengan -e untuk satu liner:sed -e '/<TEXT1>/{r File1' -e 'd}' File2
sdaau

1
Dan bagaimana jika alih-alih mengganti seluruh baris yang berisi <TEXT1>, saya hanya ingin mengganti string itu sendiri, meninggalkan sisa garis utuh? Text1: <TEXT1>untuk Text1: <file_contents>.
Robin Winslow

9

Butuh waktu lama untuk menemukan solusi ini menggunakan penggantian var. Semua solusi sed tidak bekerja untuk saya, karena mereka menghapus baris lengkap atau mengganti secara tidak benar.

FILE2=$(<file2)
FILE1=$(<file1)
echo "${FILE2//TEXT1/$FILE1}" 

Mengganti semua kejadian TEXT1 dalam file2 terhadap konten file1. Semua teks lainnya tetap tidak tersentuh.


sangat bagus. mungkin lebih cepat daripada sedterlalu, karena "ekspansi" (alias penggantian) dibangun ke dalam shell ( bashsetidaknya)
kuning

7

Saya menjawab karena metode diff/ patchmungkin menarik dalam beberapa kasus. Untuk menentukan substitusi baris yang terkandung dalam file blob1dengan baris yang terkandung dalam blob2penggunaan:

diff -u blob1 blob2 > patch-file

Misalnya, jika blob1mengandung:

hello
you

dan blob2mengandung:

be
welcome
here

yang dihasilkan patch-fileadalah:

--- blob1   2011-09-08 16:42:24.000000000 +0200
+++ blob2   2011-09-08 16:50:48.000000000 +0200
@@ -1,2 +1,3 @@
-hello
-you
+be
+welcome
+here

Sekarang, Anda dapat menerapkan tambalan ini ke file lain:

patch somefile patch-file

Ini akan menggantikan hello, yougaris dengan be, welcome, herebaris dalam somefile.


ini sangat pintar tetapi akan lebih baik jika Anda bisa mengotomatiskannya dalam skrip
qodeninja
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.