當前位置: 首頁>>技術教程>>正文


如何替換多個文本文件第 5 行的字符串?

, ,

問題描述

我想使用單個終端命令將多個文本文件(file1.txt、file2.txt、file3.txt、file4.txt)的第 5 行替換為字符串“Good Morning”。

所有文本文件都位於我的 ~/Desktop 上。

注意:我的桌麵由 6 個 .txt 文件組成。我隻想將更改應用於上述 4 個文本文件。

最佳答案

這裏有一些方法。我正在使用 brace expansion ( file{1..4}.txt ) 這意味著 file1.txt file2.txt file3.txt file4.txt

  1. Perl perl -i -pe 's/.*/ Good Morning / if $.==5' file{1..4}.txt
    解釋:

    • -i :使 perl 就地編輯文件,更改原始文件。如果 -i 後跟文件擴展名後綴,則為每個修改的文件創建備份。例如:如果 file1.txt 在執行過程中被修改,-i.bak 創建一個 file1.txt.bak

    • -p :表示逐行讀取輸入文件,應用腳本並打印。

    • -e :允許您從命令行傳遞腳本。

    • s/.*/ Good Morning / :這會將當前行 ( .* ) 中的文本替換為早安。

    • $. 是一個特殊的 Perl 變量,用於保存輸入文件的當前行號。因此, s/foo/bar/ if $.==5 表示僅在第 5 行用 bar 替換 foo

  2. sed

    sed -i '5s/.*/ Good Morning /' file{1..4}.txt
    

    解釋:

    • -i :與 perl 一樣,就地編輯文件。

    默認情況下,sed 打印輸入文件的每一行。 5s/pattern/replacement/ 表示第 5 行替換模式。

  3. awk

    for f in file{1..4}.txt; do 
        awk 'NR==5{$0=" Good Morning "}1;' "$f" > foobar && mv foobar "$f"; 
    done
    

    解釋:

    awk-i 選項沒有等價物¹,這意味著我們需要創建一個臨時文件 ( foobar ),然後將其重命名以覆蓋原始文件。 bash 循環 for f in file{1..4}.txt; do ... ; done 簡單地遍曆每個 file{1..4}.txt ,將當前文件名保存為 $f 。在 awk 中, NR 是當前行號, $0 是當前行的內容。因此,腳本將僅在第 5 行將行 ( $0 ) 替換為“早安”。 1;awk 用於“打印行”。

    ¹較新的版本與他的 answer 中顯示的 devnull 一樣。

  4. 核心工具

    for f in file{1..4}.txt; do 
        (head -4 "$f"; echo " Good Morning "; tail -n +6 "$f") > foobar && 
        mv foobar "$f"; 
    done 
    

    解釋:

    循環在上一節中進行了解釋。

    • head -4 : 打印前 4 行

    • echo " Good Morning " : 打印“早安”

    • tail -n +6 :打印從第 6 行到文件末尾的所有內容

    這三個命令周圍的括號 ( ) 允許您捕獲所有三個命令的輸出(因此,第 4 行,然後是“早上好”,然後是其餘行)並將它們重定向到一個文件。

次佳答案

您可以使用 sed

sed '5s/^/Good morning /' file

Good morning 附加到文件的第五行。

如果要替換第 5 行的內容,請說:

sed '5s/.*/Good morning/' file

如果您想就地保存對文件的更改,請使用 -i 選項:

sed -i '5s/.*/Good morning/' file

sed 一次可以處理多個文件。您可以在命令的末尾添加更多文件名。您還可以使用 bash 擴展來匹配特定文件:

# manually specified
sed -i '5s/.*/Good morning/' file1.txt file2.txt file3.txt file4.txt

# wildcard: all files on the desktop
sed -i '5s/.*/Good morning/' ~/Desktop/*

# brace expansion: file1.txt, file2.txt, file3.txt, file4.txt
sed -i '5s/.*/Good morning/' file{1..4}.txt

can read more about brace expansions here


GNU awk 版本 4.1.0 及更高版本帶有 an extension,可啟用就地編輯。所以你可以說:

gawk -i inplace 'NR==5{$0="Good morning"}7' file

Good morning 替換文件中的第 5 行!

參考資料

本文由Ubuntu問答整理, 博文地址: https://ubuntuqa.com/zh-tw/article/11933.html,未經允許,請勿轉載。