O que este comando grep e sed faz

O que este comando grep e sed faz

Eu já sei o que partes deste comando fazem:

zgrep -v "org" /path/to/files/* | zgrep "FollowEvent" | zgrep -o 'login":"[^"]*"' | cut -d'"' -f3 | sort | uniq -c | sed '1i{
       s/\s*\([0-9]*\)\s*\(.*\)/"\2": \1,/;$a}' > usernames_followevents.txt

Peça por peça:

1) zgrepé usado para grep(pesquisar) .json.gzarquivos

2) zgrep -v "org" /path/to/files/*significa encontrar entradas em cada arquivo /path/to/files/*que não contenham "org".

3) |é um cano; significa "e então"

4) zgrep "FollowEvent"significa encontrar a string "FollowEvent"dentro dos resultados encontrados no primeiro zgrep.

5) |é um cano; significa "e então"

6) zgrep -o 'login":"[^"]*"'significa encontrar correspondências não vazias para a string login":"e todo o texto após a palavra `login' na entrada.

7) | cut -d'"' -f3significa “e então pegar apenas o terceiro campo da correspondência resultante”, que é, neste caso, um nome de usuário.

8) | sort | uniq -csignifica "e então classificar os nomes de usuário e contar o número de instâncias exclusivas de cada nome de usuário".

Até agora, temos:

zgrep -v "org" /path/to/files/* | zgrep "FollowEvent" | zgrep -o 'login":"[^"]*"' | cut -d'"' -f3 | sort | uniq -c

que é encontrar, em todas as entradas em todos os arquivos em /path/to/files/* que não contêm a string "org", mas contêm a string "FollowEvent", todos os nomes de usuário (que é o texto no terceiro campo após " login") e, em seguida, classificar esses nomes de usuário e contar o número de vezes que cada nome de usuário aparece.

Meu problema é com esta parte:

sed '1i{ s/\s*\([0-9]*\)\s*\(.*\)/"\2": \1,/;$a}'

Eu sei (ou acho que sei) isto:

1) sedé um editor de stream que permite a manipulação de texto.

2) sed '1i{significa "na linha anterior, insira {"

3) No total, este comando retorna {"username":count of that username}para todos os nomes de usuário em todos os arquivos, conforme discutido anteriormente. Em seguida, ele os coloca em um arquivo chamado usernames_followevents.txt.

4) A parte "\2":significa "coloque aspas duplas ao redor do nome de usuário, que é o segundo campo (?) e depois insira:".

Gostaria de manipular o sedcomando, mas sem entender o resto dos detalhes não posso começar a fazer modificações.

Alguém poderia explicar o que cada parte do sedcomando está fazendo?

Responder1

A maneira como o comando sed está escrito agora está incorreta. Deve ser um script como este:

1i{
s/\s*\([0-9]*\)\s*\(.*\)/"\2": \1,/
$a}

ou em uma única linha como esta:

sed -e '1i{' -e 's/\s*\([0-9]*\)\s*\(.*\)/"\2": \1,/' -e '$a}'

Literalmente tudo o que você coloca após os comandos ie aaté uma nova linha ou final de expressão (com -e) é impresso diretamente na saída padrão.

Quanto ao que faz, vamos decompô-lo:

1i{

1é um endereço de linha. Diz ao sed quando executar um comando. Quando o conteúdo da primeira linha é lido no espaço padrão (sem a nova linha final), ele iinsere '{' na saída padrão em uma linha separada. Observe que o espaço padrão permanece inalterado, não foi adicionado '{' a ele.

sé o comando de busca e substituição, o comando mais versátil do sed. \scorresponde a um espaço em branco. \(regex\)está agrupando o regex dentro dele como em matemática, mas também armazena o que foi correspondido por ele em um registro numérico baseado na ordem desse grupo: \1 a \9.

A saída de uniq -cé algo assim:

    occurrences string
    3 user

Agora a parte complicada:

\s*\([0-9]*\)\s*\(.*\)

Ainda na linha 1. O espaço padrão é um monte de espaços, depois '3 usuários'. Para corresponder a isso, procuramos o espaço em branco zero ou mais vezes, depois um dígito muitas vezes, que é um número (na minha opinião deveria ter sido + em vez de *) que está armazenado no registro \1, então o espaço (* é não é necessário, eu acho), então qualquer caractere muitas vezes (novamente + teria sido melhor) que está armazenado no registro \2. Então agora, a ocorrência está em \1 e string/user em \2.

"\2": \1,

A linha inteira foi correspondida e as partes foram armazenadas, agora substituímos o que foi correspondido por aspas, depois usuário, depois aspas, dois pontos, espaço, ocorrência e vírgula.

$a}

$também é um endereço de linha. Se a linha atual for a última, no momento não, chame o acomando para anexar '}' à saída padrão em uma linha separada.

Este é o fim do processamento do código para esta linha, a impressão automática do espaço do padrão tal como está após a manipulação ser feita, então o conteúdo da segunda linha é lido e todo o ciclo se repete.

Exemplo de saída:

{
"user": 3,
}

Esse é basicamente um formato de arquivo JSON, embora indentado incorretamente.

É isso. Desculpe por escrever romances :)

informação relacionada