删除模式上方的线

Delete the line above a pattern

我正在尝试删除文件中包含特定模式的行以及该特定模式正上方的行。模式是 'Query '。该文件看起来像这样:

1. Query= ENST00000641267.1
2. Query= ENST00000641448.1
3. Query= MSTRG.3294.1
4. Query= ENST00000435134.2
5. Query= ENST00000503142.1
6. Query= ENST00000503142.1
7. Query    8  THSLRYFRLGVSDPIHGVPEFISVGYVDSHPITTYDSVTQQKEPRAPWMAENLVPDHWER 187
8. Query  188  YTQLLKGWQQMFRVELKRQQRHYNHSGSHTYQRMIGCELLEDGSTTGFLQYAYDGQNFLI 367
9. Query  368  FNKDTLS*LAVDNVAHTIKRAREANQHELQYQKNWLEEECIA*LKRFLEYGKDTQQ 535
10. Query= ENST00000612670.1
11. Query    1  MVFTQAPAEIMGHLRICSLLARQCLAEFLGVFVLMLLTQGAVAQAVTSGETKGNFFTMFL 180
12. Query  181  AGSLAVTIAIYVGGNVSG 234
13. Query= MSTRG.3309.1

因此应删除第 6 到 12 行,而应保留所有其他行。我尝试了以下方法来删除模式之前的行,但无法让它工作:

tac | sed '/Query /'I, +1 d' | tac file.txt > newfile.txt

它只是输出'>'符号。 有人可以帮忙吗?

期望的输出是:

    1. Query= ENST00000641267.1
    2. Query= ENST00000641448.1
    3. Query= MSTRG.3294.1
    4. Query= ENST00000435134.2
    5. Query= ENST00000503142.1
    13. Query= MSTRG.3309.1

谢谢!

我会按照以下方式使用 GNU AWK,令 file.txt 内容为

1. Query= ENST00000641267.1
2. Query= ENST00000641448.1
3. Query= MSTRG.3294.1
4. Query= ENST00000435134.2
5. Query= ENST00000503142.1
6. Query= ENST00000503142.1
7. Query    8  THSLRYFRLGVSDPIHGVPEFISVGYVDSHPITTYDSVTQQKEPRAPWMAENLVPDHWER 187
8. Query  188  YTQLLKGWQQMFRVELKRQQRHYNHSGSHTYQRMIGCELLEDGSTTGFLQYAYDGQNFLI 367
9. Query  368  FNKDTLS*LAVDNVAHTIKRAREANQHELQYQKNWLEEECIA*LKRFLEYGKDTQQ 535
10. Query= ENST00000612670.1
11. Query    1  MVFTQAPAEIMGHLRICSLLARQCLAEFLGVFVLMLLTQGAVAQAVTSGETKGNFFTMFL 180
12. Query  181  AGSLAVTIAIYVGGNVSG 234
13. Query= MSTRG.3309.1

然后

awk 'NR>1&&!/Query /&&prev!~/Query /{print prev}{prev=[=11=]}END{if(prev!~/Query /){print prev}}' file.txt

输出

1. Query= ENST00000641267.1
2. Query= ENST00000641448.1
3. Query= MSTRG.3294.1
4. Query= ENST00000435134.2
5. Query= ENST00000503142.1
13. Query= MSTRG.3309.1

说明:我使用 prev 变量来存储上一行,如果当前行不匹配 Query 并且上一行不匹配 Query 那么我打印上一行。由于我 print 前一行我需要单独考虑最后一行,为此我使用 END.

(在 GNU Awk 5.0.1 中测试)

这可能适合您 (GNU sed):

sed '$!N;/\n.*Query /D;/Query /!P;D' file

追加下一行(除非当前行是最后一行)。

如果附加行包含Query ,请删除第一行并重新开始。

如果第2行window的第一行包含Query ,则不打印。

否则打印两行中的第一行,删除它并重新开始。

N.B。追加下一行取决于它不是最后一行,因为 sed 的默认行为是打印模式 space 如果调用 N 命令以读取文件末尾。这允许正确处理最后一行,即如果最后一行包含 Query 它将被删除。

$ tac file | awk '/Query /{c=2} !(c&&c--)' | tac
1. Query= ENST00000641267.1
2. Query= ENST00000641448.1
3. Query= MSTRG.3294.1
4. Query= ENST00000435134.2
5. Query= ENST00000503142.1
13. Query= MSTRG.3309.1

有关详细信息,请参阅 Printing with sed or awk a line following a matching pattern