awk 缓冲区变量以加速行的解析

awk buffer variables to speed up parsing of lines

接上次 post

我想缓冲字段的结果以加速日志行的解析。
我试过了
awk 'BEGIN{OFS=","} { FS="\""; [=10=]=[=10=]; CIP=; (buffer[CIP]==0) { cmd="geoiplookup "CIP; cmd | getline buffer[CIP]; close(cmd) } ... print "CIP,..." >> mysql.infile }'

但是我收到语法错误...

CIP=[ip 地址]
所以我试图缓冲 IP 地址,这样它就不会一直 运行 geoiplookup 脚本,因为它会减慢解析速度...

感谢任何帮助...

我没有看到缓冲的直接问题,因为它似乎在这个例子中有效::

echo "172.217.22.132\n172.217.22.132" | \
     awk '{CIP=}
      (buffer[CIP]==0) { print "Calling geoiplookup";
        cmd="geoiplookup "CIP;
        cmd | getline buffer[CIP];
        close(cmd) }
      {print buffer[CIP]}'

这会产生:

Calling geoiplookup
GeoIP Country Edition: US, United States
GeoIP Country Edition: US, United States

如您所见,它只被调用一次,所以缓冲有效。

但是您的代码中存在一个错误,下面的代码应该会更好。

awk  'BEGIN{OFS=","}
{ FS="\""; [=12=]=[=12=]; CIP=; }
(buffer[CIP]==0) { cmd="geoiplookup "CIP; cmd | getline buffer[CIP]; close(cmd) }
...
{print "CIP,..." >> mysql.infile }' 

我认为这里的主要问题是对awk语法的理解。

在其简单形式中,您应该将 awk 理解为 linerecord 解析器。 awk 语言是建立在一组

形式的规则之上的
pattern1 { action1 }
pattern2 { action2 }
...

应该理解为:如果满足pattern1,则在当前行执行action 1。然后继续pattern2。如果没有给出模式,则假定为 true 并执行相应的操作。

在上面的第一个例子中,有 3 个规则。

  • {CIP=} 声明作为第一个操作将变量 CIP 设置为 </code></li> <li><code>(buffer[CIP]==0) { print ... } 声明第二个操作 (print ...) 仅在 buffer[CIP] 为零时执行,即该值尚未计算。
  • 最终规则规定打印缓冲值。

希望对您有所帮助。