awk - substitui o número maior que 17 dígitos em uma coluna com -

3

Eu tenho um arquivo CSV contendo valores de timestamp no UTC que preciso substituir por - . Pode haver mais de um timestamp na mesma coluna, por favor, deixe-me saber como faço isso?

Por exemplo, esta é uma coluna em um arquivo CSV:

+1234|2|12|1|1|1537820114232192380|0  +1234|2|12|1|1|1537820113262689150|0

A saída deve se parecer com:

+1234|2|12|1|1|-|0  +1234|2|12|1|1|-|0
    
por Yashovan N 03.10.2018 / 00:51

4 respostas

3

Como isso está dentro de um file , é mais rápido usar o sed:

sed -i 's/[0-9]\{18,\}/-/g' file

Entenda que a opção -i alterará seu arquivo. Se você quiser ver o que ele faz antes de confirmar, remova o -i .

Note que no BSD, o -i deve ter um parâmetro, então use: -i '' .

O Awk também pode fazer isso:

<file awk '{gsub("[0-9]{18,}", "-")}1'  >newfile
    
por 03.10.2018 / 02:29
3

Você pode usar awk da seguinte forma:

echo "+1234|2|12|1|1|1537820114232192380|0  +1234|2|12|1|1|1537820113262689150|0" | awk '{gsub("[0-9]{18,}", "-")}1'
  +1234|2|12|1|1|-|0  +1234|2|12|1|1|-|0

Você pode usar sed da seguinte forma:

  echo "+1234|2|12|1|1|1537820114232192380|0  +1234|2|12|1|1|1537820113262689150|0" | sed -r 's/[0-9]{18,}/-/g'
  +1234|2|12|1|1|-|0  +1234|2|12|1|1|-|0
    
por 03.10.2018 / 01:41
1

Se, por qualquer razão, você quiser evitar usar expressões regulares ou ferramentas além do awk, você pode optar por usar condicionais do awk .

echo "+1234|2|12|1|1|1537820114232192380|0  +1234|2|12|1|1|1537820113262689150|0" | awk -F'|' 'OFS="|" { for (i = 1; i <= NF; i++) { if (length($i) > 17) { $i = "-"} } print; }'

+1234|2|12|1|1|-|0  +1234|2|12|1|1|-|0

Explicação:

-F'|'                            # Set input field-separator to bar
'OFS="|"                         # Set output field-separator to bar
{ for (i = 1; i <= NF; i++) {    # Loop through the fields
if (length($i) > 17) { $i = "-"} # Set a field with length over 17 to "-"
} print; }'                      # Print output of all fields after this process
    
por 03.10.2018 / 16:56
0

Eu usaria essa variante usando awk (e sed para substituir o ORS à direita por newline), que verifica strings de comprimento de 17 caracteres ou mais.

awk -vRS='[|\n]' -vORS='|' 'length($0)>=17{$0="-"}1' | sed 's/|$/\n/'

Para filtrar apenas números com mais de 17 dígitos, faça:

awk -vRS='[|\n]' -vORS='|' 'log($0)/log(2)>=17{$0="-"}1' | sed 's/|$/\n/'

Também existem truques para evitar o sed e usar um único processo do awk, como aqui: link

Dessa forma, usamos os recursos de divisão e filtragem de registros do awk, e podemos ter um controle mais preciso do filtro, em oposição a uma expressão regular.

Teste de validação:

$ awk -vRS='[|\n]' -vORS='|' 'length($0)>=17{$0="-"}1' <<< '+1234|2|12|1|1|1537820114232192380|0  +1234|2|12|1|1|1537820113262689150|0' | sed 's/|$/\n/'
+1234|2|12|1|1|-|0  +1234|2|12|1|1|-|0

$ awk -vRS='[|\n]' -vORS='|' 'log($0)/log(2)>=17{$0="-"}1' <<< '+1234|2|12|1|1|1537820114232192380|0  +1234|2|12|1|1|1537820113262689150|0' | sed 's/|$/\n/'
+1234|2|12|1|1|-|0  +1234|2|12|1|1|-|0
    
por 03.10.2018 / 13:33