Contagem de ocorrências de linha em múltiplos arquivos

0

Eu tenho arquivos de log que eu preciso para grep e contar o número de ocorrências de uma linha específica.

O problema é que devo começar em uma linha específica do primeiro arquivo e contar apenas ocorrências após essa linha. Todos os outros arquivos devem ser pesquisados completamente. Apenas o primeiro arquivo precisa estar limitado às últimas x linhas.

Depois, preciso multiplicar o resultado por 200. Gostaria de fazer isso com um único comando.

Aqui está um exemplo de trabalho que funciona com 2 arquivos de log, mas eu precisarei expandir isso para 3 arquivos em breve e espero que alguém encontre uma maneira melhor de fazer isso:

expr 'tail -n 5147 Log1.log.2013-11-18 | grep "The line I need to count" | wc -l' + 'cat Log2.log | grep "The line I need to count" | wc -l' | awk '{print $1"*200"}' | bc
    
por FGreg 20.11.2013 / 02:04

2 respostas

1

Uma solução geral para números arbitrários de arquivos:

 for file1 in log1.txt log2.txt logN.txt; do
   for file2 in logA.txt logB.txt logC.txt; do
     for file3 in logD.txt logE.txt logF.txt; do
     match1=$(tail -n 5147 $file1 | grep -c 'The line');
     match2=$(grep -c "the line" $file2);
     match3=$(grep -c "the line" $file3);
     echo "($match1 + $match2 + $match3) * 200" | bc;
   done;
 done;
done

Isso contará as ocorrências de the line nas últimas 5147 linhas de cada $file1 s e salvará isso como $match1 . Em seguida, ele contará as ocorrências de the line em cada uma das $file2 s e as salvará como match2 e o número de ocorrências em cada file3 as $match3 . Então, calculará ($match1 + $match2 + $match3) * 200 .

Basta adicionar mais um arquivo ao que você está fazendo e corrigir sua sintaxe:

echo "$(tail -n 5147 Log1.log.2013-11-18 | grep -c 'The line') \ 
      $(grep -c 'The line' Log2.log) $(grep -c 'The line' Log3.log)" | 
        awk '{print ($1+$2+$3)*200}' 

Existem alguns truques aqui. grep -c conta correspondências em vez de imprimi-las, portanto, não há necessidade de wc . awk pode fazer matemática, então não há necessidade de bc . Eu uso echo em vez de expr porque eu não estou mais fazendo aritmética no shell, apenas ecoando os resultados das três pesquisas e passando-as para awk . Isso deve resultar em algo como:

echo "10 4 12" | awk '{print ($1+$2+$3)*200}' 

Uma versão mais concisa:

echo $((($(tail -n 5147 Log1.log.2013-11-18 | grep -c "The line) + \ 
         $(grep -c "The line" Log2.log) + $(grep -c "The lne" Log3.log)) * 200))

Isso faz toda a matemática no shell, usando a notação $(( )) . Você pode tentar com echo $((2*4)) . Não é muito fácil de ler, ele se expande para:

echo "$(( ($file1_matches + $file2_matches + $file3_matches) * 200 ))"
    
por 20.11.2013 / 02:32
2

Acho que você deve adicionar o terceiro arquivo depois do segundo gato:

expr 'tail -n 5147 Log1.log.2013-11-18 | grep "The line I need to count" | wc -l' + 'cat Log2.log Log3.log | grep "The line I need to count" | wc -l' | awk '{print $1"*200"}' | bc

exemplo:

$ echo abc > 1.txt 
$ echo cde > 2.txt 
$ echo def > 3.txt 
$ cat 1.txt 2.txt 3.txt | grep d 
cde 
def
    
por 20.11.2013 / 02:20

Tags