Como dividir um arquivo grande em vários menores com base no valor de uma coluna de texto?

2

Eu tenho um arquivo grande que preciso dividir em partes viáveis. (350 milhões de registros) A chave é o segundo valor da coluna não pode estourar no próximo arquivo.

A leitura e a escrita são longas, o comando split não funciona. mais alguma coisa que eu possa fazer?

arquivo de exemplo com 10 registros a serem divididos em 3 arquivos de saída:

aa,22,xxx
aa,22,xxx
aa,22,xxx
aa,22,xxx
aa,22,xxx
aa,23,xxx
aa,23,xxx
aa,23,xxx
aa,23,xxx
aa,24,xxx

output1:

aa,22,xxx
aa,22,xxx
aa,22,xxx
aa,22,xxx
aa,22,xxx

output2:

aa,23,xxx
aa,23,xxx
aa,23,xxx
aa,23,xxx

output3:

aa,24,xxx
    
por Sal Esposito 09.11.2016 / 15:09

2 respostas

4

com awk :

awk -F, '$2 != ref { i++; ref = $2 } { print $0 >"output" i }' input

dividirá input de acordo com a segunda coluna nos arquivos output1 , output2 ...

Se você quiser limitar o número de linhas por arquivo de saída:

awk -F, '$2 != ref { i++; ref = $2; lines = 0 } lines >= 1000 { i++; lines = 0 } { print $0 >"output" i; lines++ }' input

produzirá arquivos de saída contendo no máximo 1000 linhas, respeitando a restrição na segunda coluna.

Aqui está outra variante, que divide na próxima alteração na segunda coluna após um determinado limite ter sido atingido (1000 linhas neste exemplo, você usaria 50000000 presumivelmente):

awk -F, 'BEGIN { change = 1 } change && $2 != ref { i++; ref = $2; change = 0; lines = 0 } lines >= 1000 { change = 1 } { print $0 >"output" i; lines++; ref = $2 }' input
    
por 09.11.2016 / 15:14
4

Usando Miller :

$ mlr --nidx --fs comma put -q 'tee > $2 . ".dat", $*' ten.dat

$ cat 22.dat
aa,22,xxx
aa,22,xxx
aa,22,xxx
aa,22,xxx
aa,22,xxx

$ cat 23.dat
aa,23,xxx
aa,23,xxx
aa,23,xxx
aa,23,xxx

$ cat 24.dat
aa,24,xxx
    
por 11.11.2016 / 13:40