Sed - 匹配但不包括模式,包括换行符

Sed - 匹配但不包括模式,包括换行符

我有一个多 fasta 格式的输入。本质上:

>header1
AAAAAATTTTCCCCGGGG
AAAATGTGTGTCTCTCTC
ATAGGATGAGT
>header2
GGGGTGTGTGATGTAGTA
AAAATGTGTGTCTCTCTC
ATAGGATGAGT
....
>header720
GGGGTGCTCGCTCTGTGA
AAAATGAGTCATCATTGT
ATAGGATGAGT

我有兴趣以这种格式恢复条目 #28:

>header28
GGGGTGCTCGCTCTGTGA
AAAATGAGTCATCATTGT
ATAGGATGAGT

我最初的尝试是使用 sed。但是, sed -n '/header28/,/>/p'('获取从与模式匹配的行到下一个符号的所有内容 >') 会导致:

>header28
GGGGTGCTCGCTCTGTGA
AAAATGAGTCATCATTGT
ATAGGATGAGT
>header29

同时,sed -n '/header28/,/[^>]*/p'('获取从与模式匹配的行到但不包括符号>'的所有内容)会导致比我需要的更短的序列,因为它卡在换行符上,如下所示:

>header28
GGGGTGCTCGCTCTGTGA

此外,这些选项都没有处理该条目是列表中最后一个条目的可能性(因此后面没有另一个>)。这是不可能的,我可以忍受它,但是也可以处理这个问题的代码会很棒。

非常感谢您的帮助!对 sed 之外的其他选项持开放态度,但我认为我的目标是简单的东西。

答案1

最有可能的是,这已经被问过......但无论如何,只需删除范围结束(如果存在):

sed  '/>header28/,/>/!d;/>/{
     />header28/!d
     }' infile

答案2

使用任何 awk:

$ awk '/^>/{f=(/>header28$/)} f' file
>header28
GGGGTGCTCGCTCTGTGA
AAAATGAGTCATCATTGT
ATAGGATGAGT

或者更有效的是,您可以在打印该块后退出,而不是继续读取其余输入:

$ awk '/^>/{if (f) exit; f=(/>header28$/)} f' file
>header28
GGGGTGCTCGCTCTGTGA
AAAATGAGTCATCATTGT
ATAGGATGAGT

答案3

awk

awk -v hdrId='header28' '
  /^>header/ && buf{ printf("%s", buf); exit }
  $0 ~ "^>" hdrId "$" || buf{ buf=buf $0 ORS }' infile

答案4

我会使用 FastaToTbl 和 TblToFasta 脚本(请参阅此处的脚本)我在其他答案中提到过,只需执行以下操作:

$ FastaToTbl file.fa | grep -w header28 | TblToFasta
>header28 
GGGGTGCTCGCTCTGTGAAAAATGAGTCATCATTGTATAGGATGAGT

请注意,这会将序列分成 60 个字符的行,这在 20 年前编写这些脚本时曾是常态。由于这是 fasta,我假设不需要保留原始行折叠。如果情况并非如此,请告诉我。

相关内容