在bash脚本中使用awk根据特定行中的字符数选择行范围

在bash脚本中使用awk根据特定行中的字符数选择行范围,bash,awk,text-processing,Bash,Awk,Text Processing,这似乎是在一个长awk命令中可能实现的。但我对awk还不太了解,无法胜任 我想从第2行开始,确定每4行输入中A、T、G和C字符的总数。如果任何行号是4的倍数,其字符计数在1000到3000之间,那么我希望它打印该行以及上面的行和下面的两行 我可以将其分解,并在单独的代码行中完成其中的一部分。但当我有数百万行时,计算起来就太长了。我需要一个强大的awk命令。awk一定有足够聪明的人来解决这个问题 非常小的示例,范围10

这似乎是在一个长awk命令中可能实现的。但我对awk还不太了解,无法胜任

我想从第2行开始,确定每4行输入中A、T、G和C字符的总数。如果任何行号是4的倍数,其字符计数在1000到3000之间,那么我希望它打印该行以及上面的行和下面的两行

我可以将其分解,并在单独的代码行中完成其中的一部分。但当我有数百万行时,计算起来就太长了。我需要一个强大的awk命令。awk一定有足够聪明的人来解决这个问题

非常小的示例,范围10<字符计数<40: 输入:

@d0aec33d-ba    
TCAGTATGCTTCGTGCAATCAAG    
+    
-0(''$&"('    
@ee487ad3-b71    
ACAATGTG    
+    
""%#0&'+367<677
这里有一个简单的例子:

$ awk '
NR%4==1 { b="" }                                # first record of four, reset buffer
NR%4==2 && length()>10 && length()<40 { f=1 }   # 2/4 if length is right, flag up
{ b=b $0 ORS }                                  # buffer records to b
NR%4==0 && f {                                  # 4/4 
    printf "%s",b                               # print if flag is up
    f=0                                         # and flag down
}' file                 
编辑:

参数化版本x=$min,y=$max:

一条班轮,以防万一:

$ awk -v x=$min -v y=$max 'NR%4==1{b=""} NR%4==2 && length()>x && length()<y{f=1} {b=b $0 ORS} NR%4==0 && f{printf "%s",b; f=0}' file

哇,这太快了,我还没有在更大的数据集上测试它,但我看不出它在哪里考虑了固定的。使用瀑布模型:d注释中的最后一个块{printf b f==0}是错误的。如果命令在同一行上,它应该有一个分号,a=而不是==,即:{printf b;f==0}。它可能是printf b。用printf%s替换它,b应该可以解决这个问题。效果很好,修复得很好,代码很漂亮!第四行中除了A、T、G或C之外,还有其他字符吗?我不知道您的要求是什么意思,我无法想象对它们的任何解释如何从您发布的示例输入中产生您发布的预期输出。idk如果其他人运气更好,但你可能想澄清你想做什么,并解释为什么这是预期的结果。
@d0aec33d-ba
TCAGTATGCTTCGTGCAATCAAG
+
-0(''$&"('
$ awk -v x=$min -v y=$max '
NR%4==1 { b="" }                                # first record of four, reset buffer
NR%4==2 && length()>x && length()<y { f=1 }     # 2/4 if length is right, flag up
{ b=b $0 ORS }                                  # buffer records to b
NR%4==0 && f {                                  # 4/4 
    printf "%s",b         #                     # print if flag is up
    f=0                 # #                     # and flag down
    # printf b; f=0   # # # # # # # # # # # # # # if commands on the same line                        
}' file                 # #
                          #
$ awk -v x=$min -v y=$max 'NR%4==1{b=""} NR%4==2 && length()>x && length()<y{f=1} {b=b $0 ORS} NR%4==0 && f{printf "%s",b; f=0}' file