按顺序将与某个模式匹配的多个文件中的行替换为另一个文件中的行

按顺序将与某个模式匹配的多个文件中的行替换为另一个文件中的行

我想从另一个文件中按顺序替换与多个文件中的模式匹配的行,我最多有 500 个 txt 文件,其结构: 测试1.txt、测试2.txt、测试3.txt...

11111
22222
mock
55555
77777

因此,逐个读取文件,我们希望将第一个 test1.txt 文件中的模拟行替换为 mock.txt 文件中的第一行,在第二个 test2.txt 中将模拟行替换为 mock.txt 文件中的第二行,其结构如下:

模拟.txt

randomText1
randomText2
randomText3
randomText4
randomText5

依此类推,直到文件夹中的最后一个 .txt 文件

答案1

通过 GNU sed,您可以使用

cat mock.txt | sed -i -e '/mock/{R/dev/stdin' -e 'd;}' test{1..3}.txt

GNU 特定R命令读取并插入一个单身的一次一行,不像标准r选项会插入所有内容。

$ head test{1..3}.txt
==> test1.txt <==
11111
22222
randomText1
55555
77777

==> test2.txt <==
11111
22222
randomText2
55555
77777

==> test3.txt <==
11111
22222
randomText3
55555
77777
R filename

在当前周期结束时或在读取下一个输入行时将要读取的文件名行排队并插入到输出流中。请注意,如果无法读取文件名,或者到达其末尾,则不会附加任何行,并且不会出现任何错误指示。

与 r 命令一样,文件名支持特殊值 /dev/stdin,它从标准输入读取一行。

请注意,在这种情况下,直接从文件读取行/mock/R mock.txt不起作用,因为选项-i暗示-s选项,所以第一行mock.txt插入到每个文件中。

答案2

使用 GNU awk(即gawk)你可以这样做:

gawk -i inplace '/mock/ { getline < "mock.txt" } 1' test{1..3}.txt

与 一样sedgawk提供就地编辑。上面的命令查找 regex-pattern mock,当找到它时,它会将其替换为 中的下一行mock.txt。这1是一个始终匹配的模式,因此会导致gawk执行其默认操作,即打印(新)读取的行。请注意,在就地编辑期间您实际上不会看到这一行;打印动作对于记录输出是必要的。

相关内容