Como usar o AWK para consultar um arquivo carregado com o mapfile [closed]

1

Estou usando o awk no Ubuntu para correlacionar referências entre dois arquivos de log (In.log e Out.log). Ele está funcionando como esperado, mas foi o tamanho do aumento Out.log (~ K linhas), o aumento do tempo de processamento também! Então, eu queria saber, para reduzir o acesso ao disco, se eu posso carregar este arquivo Out.log na memória uma vez antes do loop, usando o comando MAPFILE ou algo semelhante, mas eu não vejo exemplos úteis. Alguma sugestão?

IN.LOG:

2016-10-20 19:20:00,IN,DEU00000000159560100
2016-10-22 19:22:20,IN,DEU00000000159560511
2016-10-24 19:24:20,IN,DEU00000000159560382
2016-10-26 19:26:20,IN,DEU00000000159560609
2016-10-28 19:28:20,IN,DEU00000000159560809

OUT.LOG:

2016-10-20 19:20:30,OUT,DEU00000000159560100
2016-10-21 19:21:30,OUT,DEU00000000159560510
2016-10-22 19:22:30,OUT,DEU00000000159560511
2016-10-23 19:23:30,OUT,DEU00000000159560381
2016-10-24 19:24:30,OUT,DEU00000000159560382
2016-10-25 19:25:30,OUT,DEU00000000159560195
2016-10-26 19:26:30,OUT,DEU00000000159560609
2016-10-27 19:27:30,OUT,DEU00000000159560433
2016-10-28 19:28:30,OUT,DEU00000000159560809
2016-10-29 19:29:30,OUT,DEU00000000159560694

Script atual:

cat IN.LOG | while read -r Line
do
    Reference=$(cut -f3 -d',' <<< $Line)
    TimeStampIn=$(cut -f1 -d',' <<< $Line)
    TimeStampOut=$(awk -F',' -v Ref=$Reference '$3==Ref {print $1; exit} ' OUT.LOG)
    echo "$Reference,$TimeStampIn,$TimeStampOut"
done
    
por Fdv 13.11.2016 / 11:58

1 resposta

1

Apenas um comando awk desta forma:

awk -v reflog=OUT.LOG '
    BEGIN{
      FS=OFS=",";
      while((getline <reflog) > 0) refs[$3]=$1;
      close(reflog)
    }{
      print $3,$1,refs[$3] ? refs[$3] : "not found"
    }' IN.LOG

Ou usando join , que é feito exatamente para casos de uso como este:

join -t, -j 3 -o 0,1.1,2.1 -a 1 -e "not found" \
  <(sort -t, -k3 IN.LOG) <(sort -t, -k3 OUT.LOG) \
  | sort -t, -k2

Note que join precisa de arquivos de entrada classificados (por "join column"). É por isso que classificamos os dois arquivos de log por coluna de referência e depois classificamos a saída novamente por data.

Ambas as ações se comportam de maneira diferente em relação a referências não exclusivas em OUT.LOG. awk ignoraria refs duplicados em OUT.LOG (o último ganha), mas join imprimia todas as correspondências. Além disso, se você adicionar -a 2 ao comando join , ele imprimirá todas linhas não paráveis.

    
por 13.11.2016 / 13:04