在 BEGIN 块中设置 RS 时跳过 AWK 中的第一行

在 BEGIN 块中设置 RS 时跳过 AWK 中的第一行

我有以下输入文件:

-Queue ID-  --Size-- ----Arrival Time---- -Sender/Recipient-------
0F2F77F472  4343854 Fri Oct  7 10:13:41  [email protected]
(host redacted.host.com[x.x.x.x] said: 452 4.2.2 Over quota (in reply to end of DATA command))
                                         [email protected]

03A017F486   992790 Fri Oct  7 13:09:44  [email protected]
(host host.redacted.net[y.y.y.y] said: 452-4.2.2 The email account that you tried to reach is over quota. Please direct 452-4.2.2 the recipient to 452 4.2.2  redacted (in reply to RCPT TO command))
                                         [email protected]

在我的 AWK 脚本中,我写了这样的内容:

BEGIN {
  RS = "\n\n"
}

{
  ... do something ...
}

标头也会得到处理,因此在我的管道中,在传递到 AWK 之前,我会执行以下操作:

... | tail +2 | awk -f script

我承认,要跳过 AWK 中的第一行,主要是通过执行以下简单技巧:

{
  if (NR > 1) {
    ...
  }
}

它应该可以工作,但是RS = "\n\n"我在块中设置的BEGIN会使第一条记录被忽略(AWK 将标头解释为第一条记录的一部分)。

测试:

$ awk 'BEGIN { RS = "\n\n" } { print NF }' sample
28
41

$ awk 'BEGIN { RS = "\n\n" } NR > 1 { print NF }' sample
41

有什么方法可以在不依赖任何外部工具的情况下实现目标?


GNU Awk 5.0.1, API: 2.0 (GNU MPFR 4.0.2, GNU MP 6.2.0)

答案1

使用任何 awk:

$ awk 'NR==1{RS=""; next} {print NF}' file
22
38

当您使用RS = "\n\n"POSIX 未定义的行为时,您需要使用 GNU awk 或任何其他专门支持多字符 RS 的 awk(请阅读 awk 的手册页)。另一方面,如果您使用RS = ""POSIX 定义的 IS 将 awk 置于段落模式,其中每个记录与下一个记录之间用空行分隔。

在读取第一行之前不设置 RS 让我们可以轻松读取并丢弃该行。

相关内容