AWK - код, который не выполняется последовательно в правиле END - PullRequest
0 голосов
/ 24 июня 2019

Я обрабатываю один файл, создавая два разных ассоциативных массива для подсчета частоты двух разных шаблонов (т. Е. Полей 3 и 6, когда они найдены).

Пример файла:

2019-06-20 : INFO : XYZ_6789 : [Command [cmd_zip_files]:] Standard output and error
2019-06-20 : INFO : ABC_1234 : License issue
Line with no timestamp
2019-06-20 : INFO : XYZ_6789 : [Command [cmd_zip_files]:] Standard output and error
2019-06-20 : INFO : ABC_1234 : License issue

Я хочу напечатать оба массива в конце, но их выходы перекрываются.

Я использую GNU Awk 4.1.3.

Я пытался использовать "next / continue«заявления, но они, кажется, не являются ответом.

Возможно, я неправильно использую правило END.

#!/usr/bin/env awk

BEGIN {
  FS="\\)? : \\(?| \\| |[][]"
  MSG_COL=3
  CMD_COL=6
  SEP="=================="
}

{
  if (match ($MSG_COL, /^[A-Z]{3}_[0-9]+/))
      msg_count[$MSG_COL]++

  if ($MSG_COL == "XYZ_6789")
    cmd_count[$CMD_COL]++
}

END {

  print ">> Count of msg <<"

  for (msg in msg_count)
    if (msg_count[msg] > 0)
      print msg_count[msg], msg | "sort -n"

  print ">> Count of cmd <<"

  for (cmd in cmd_count)
    print cmd_count[cmd], cmd | "sort -n"

}

Я ожидаю, что мой код выдаст следующий вывод:

>> Count of msg <<
2 ABC_1234
2 XYZ_6789
>> Count of cmd <<
2 cmd_zip_files

Хотя,Я получаю это:

>> Count of msg <<
>> Count of cmd <<
2 ABC_1234
2 cmd_zip_files
2 XYZ_6789

Ответы [ 2 ]

1 голос
/ 24 июня 2019

Если вы уже используете GNU Awk, вы можете избежать использования подоболочек и внешних утилит, установив PROCINFO["sorted_in"]. Ниже я использовал @val_num_desc, который сортирует по убыванию числового значения (не индекса):

awk -F ' : ' '
  /^2019/ {Msg[$3]++; if(split($4, A, "[][]") > 1) Cmd[A[3]]++}
  END {
    PROCINFO["sorted_in"]="@val_num_desc"
    print ">> Count of msg <<"
    for(m in Msg) print Msg[m], m
    print ">> Count of cmd <<"
    for(c in Cmd) print Cmd[c], c
  }
' file
>> Count of msg <<
2 XYZ_6789
2 ABC_1234
>> Count of cmd <<
2 cmd_zip_files
0 голосов
/ 25 июня 2019

Это происходит потому, что вы сами не закрываете дескрипторы открытых файлов. Awk закроет их для вас в конце концов, когда скрипт завершится, и в этот момент все ожидающие буферизованные выходные данные будут сброшены, но порядок, в котором они закрыты, не предсказуем и не надежен.

Измените блок END на явно close их в нужном вам порядке:

END {
  print ">> Count of msg <<"
  c = "sort -n"
  for (msg in msg_count)
    if (msg_count[msg] > 0)
      print msg_count[msg], msg | c
  close(c)

  print ">> Count of cmd <<"
  c = "sort -n"
  for (cmd in cmd_count)
    print cmd_count[cmd], cmd | c
  close(c)
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...