【问题标题】:Replacing every nth line in one file with next line from another file in bash用bash中另一个文件的下一行替换一个文件中的每一行
【发布时间】:2019-07-26 08:35:41
【问题描述】:

我对此很陌生,并且意识到已经发布了类似的问题,但我无法完全弄清楚我需要从他们那里得到什么。我有两个文件。

文件 1:

1: Read 1
2: Sequence 1
3: +
4: Quality 1
5: Read 2
6: Sequence 2 
7: +
8: Quality 2
...

文件 2:

1: Sequence 1 edited
2: Sequence 2 edited
3: Sequence 3 edited
4: Sequence 4 edited
...

从第一个文件的第 2 行开始,我需要将每 4 行替换为第二个文件中的下一个读取行,因此结果如下所示:

1: Read 1
2: Sequence 1 edited
3: +
4: Quality 1
5: Read 2
6: Sequence 2 edited 
7: +
8: Quality 2
...

到目前为止,我一直在使用这段代码,它似乎可以工作,但作为命令很慢,作为 shell 脚本也很痛苦:

Counter=2
while read p; do echo $Counter; echo $p; 
    sed -i~ "${Counter}s/^.*/$p/" file 1; 
    Counter=$((Counter+4)); done < file 2

我认为我应该能够使用 awk 来完成,但我不确定如何。任何帮助或改进将不胜感激!

【问题讨论】:

  • 为了便于阅读,请将单行分成多行。

标签: bash awk sed replace while-loop


【解决方案1】:

假设行号仅用于解释目的并且包含在文件中,请尝试以下操作:

awk 'NR==FNR {line[NR]=$0; next} {if (FNR%4==2) $0=line[++count]; print}' file2 file1

输出:

Read 1
Sequence 1 edited
+
Quality 1
Read 2
Sequence 2 edited
+
Quality 2
...

[解释]

  • 条件NR==FNR 仅在读取file2 时匹配并且它存储 数组line 中的行按顺序排列。
  • 以下{if ... 语句仅在读取file1 时执行。 如果 file1 的行号等于 2,模数为 4,则该行 替换为数组 line 的内容。

【讨论】:

  • 您的假设是正确的 - 很抱歉缺乏清晰性。这似乎可以解决问题,而且速度更快!非常感谢您的帮助!
  • 很高兴知道它对您有所帮助。
【解决方案2】:

另一种使用 awk 和粘贴的解决方案

awk ' { print "\n" $0 "\n" "\n" } ' file2.txt | 
     paste - file1.txt | awk -F"\t" ' {x=NR%4==2 ? $1 : $2; print x } '

使用给定的输入

$ cat cmswen1.txt
Read 1
Sequence 1
+
Quality 1
Read 2
Sequence 2
+
Quality 2

$ cat cmswen2.txt
Sequence 1 edited
Sequence 2 edited
Sequence 3 edited
Sequence 4 edited

$ awk ' { print "\n" $0 "\n" "\n" } ' cmswen2.txt | 
     paste - cmswen1.txt | awk -F"\t" ' {x=NR%4==2 ? $1 : $2; print x } '
Read 1
Sequence 1 edited
+
Quality 1
Read 2
Sequence 2 edited
+
Quality 2

Sequence 3 edited



Sequence 4 edited



$

【讨论】:

    猜你喜欢
    • 2016-11-20
    • 1970-01-01
    • 2021-01-28
    • 2012-08-25
    • 1970-01-01
    • 2014-03-01
    • 2021-04-27
    • 2017-01-12
    相关资源
    最近更新 更多