awk存储到变量中的多行

时间:2015-12-29 11:36:28

标签: awk multiline

Goodday,

我有一个以下格式的文件:

XXXXXXXXXXXYYYYYYYYAAAAAAAA
XXXXXXXXXXXIIIIIIII22222222
XXXXXXXXXXXOOOOOOOOPPPPPPPP
XXXXXXXXXXXAAAAAAAAKKKKKKKK
YYYYYYYYYYY22222222AAAAAAAA
YYYYYYYYYYY55555555BBBBBBBB
YYYYYYYYYYYGGGGGGGGKKKKKKKK
YYYYYYYYYYYQQQQQQQQ88888888

......等等。每4行第一部分(X,Y,...)保持不变,行的其余部分改变。这些行之间没有分隔符,文件非常大。

我想找到一种方法,一次使用awk读取4行,将它们存储在4个变量中和/或将RS设置为\ n,将FS设置为某些东西,因为我想在特定的位置进行比较4line-blocks.And能够输出匹配的所有4行

即如果substr(17,3) == X输出你读过的所有4条记录。

我为不提供代码道歉,但我真的不知道如何用awk做到这一点。

给定一个特定的数字,即Y = 17,脚本将查找每个记录的给定子字符串。例如:

if (subst(11:2) == 17) then    # This can be a match on any line of a 4 grouping ( ie X... ) 
print (all 4 lines - All X...) - or print a given substring of those lines.

提供样本的实际示例

if (substr($0,21,2) == "PP") { print all 4 lines in memory }

...and it would print :

XXXXXXXXXXXYYYYYYYYAAAAAAAA
XXXXXXXXXXXIIIIIIII22222222
XXXXXXXXXXXOOOOOOOOPPPPPPPP
XXXXXXXXXXXAAAAAAAAKKKKKKKK

1 个答案:

答案 0 :(得分:3)

以下简单的脚本应该至少作为一个开始有用。

awk 'substr($0,21,2) == "PP" { p=1 } # remember match
    NR % 4 { a[NR%4] = $0; next }  # collect lines a[1] through a[3]
    # We have read four lines, and are ready to print if there was a match
    p { for (i=1; i<4; ++i) print a[i]; print $0;
        # reset for next iteration
        p=0 }' filename

在所有输入行上测试第一个条件。如果它们中的任何一个匹配,我们通过将标志变量p设置为1来记住这一点(任何非零都会这样做)。条件也可以是正则表达式; /^.{20}PP/在第21位寻找“PP”。

第二个条件触发的行不是4的倍数。我们只是收集这些行,并(通过next语句)跳过脚本的其余部分。 (正如您可能知道的那样,%模运算符计算除法的余数;因此它从1到3然后循环0,1,2,......)

因此,如果我们陷入第三个条件,则意味着我们在一条线上,其行号可以被4整除;现在,条件检查p的值,如果它非零,则采取行动。

(如果它为零,我们会在没有打印任何内容的情况下失败,并且循环重新开始,NR%4等于1.)