Como adicionar os números agregados em um arquivo

1

Eu preciso escrever um script que adicione os valores da mesma string em linhas diferentes.

Por exemplo, quando um arquivo contém o seguinte:

abc,10
xyz,20,
abc,30,
ghd,40
xyz,10
O script

deve verificar a string correspondente abc , xyz etc. em um arquivo e adicionar os valores dele e redirecionar a saída para o novo arquivo.

A saída deve ser:

abc,40,
xyz,30,
ghd,40

Podemos escrever um roteiro para isso? Qualquer entrada seria útil.

    
por Nithin 09.05.2016 / 12:19

3 respostas

1

Fácil no Perl: use um hash para armazenar as somas em execução.

perl -laF/,/ -ne '
    $h{ $F[0] } += $F[1];
    }{
    print "$_,$h{$_}" for keys %h;
' input-file > output-file
  • -n lê a linha de entrada por linha
  • -l adiciona novas linhas a print
  • -a divide cada linha de entrada no array @F
  • -F/,/ diz -a para dividir em vírgulas
  • }{ é o operador "Saudação Eskimo", separa o loop -n do código que será executado no final da entrada.
por 09.05.2016 / 12:52
0

Que tal bash :

for i in $(cut -d ',' -f1 FILE  | sort | uniq)
do
    echo -n "$i", &&
    echo -n $(grep "^$i," FILE | cut -d',' -f2 | paste -sd+ - | bc)
    echo $(echo "$i" | grep -E -o ",$") || echo
done

Ou se você perderá , :

for i in $(cut -d ',' -f1 FILE  | sort | uniq)
do
    echo -n "$i", &&
    echo -n $(grep "^$i," FILE | cut -d',' -f2 | paste -sd+ - | bc) &&
    grep -E -o "$i,[0-9]+,$" FILE >/dev/null && echo ',' || echo
done

Ou se você quiser salvar a ordem dos tokens:

for i in $(cut -d ',' -f1 FILE  | awk '!seen[$0]++')
do
    echo -n "$i", &&
    echo -n $(grep "^$i," FILE | cut -d',' -f2 | paste -sd+ - | bc) &&
    grep -E -o "$i,[0-9]+,$" FILE >/dev/null && echo ',' || echo
done

Substitua FILE por um nome de arquivo real.

    
por 09.05.2016 / 13:04
0
awk -F, -v OFS=, '{
          str[$1]+=$2;
          next
     }

     END {
          for (s in str) {
              print s, str[s]
          } 
     }' filename

constrói uma matriz de associados (ou seja, digitado por uma string em vez de um inteiro) contendo os totais acumulados para cada string (campo 1).

Quando leu toda a entrada, imprime cada elemento da matriz.

ghd,40
abc,40
xyz,30

canalizar através de sort se você quiser uma saída ordenada.

    
por 10.05.2016 / 06:42