Leitura de um arquivo de texto e impressão das palavras caractere por caractere de cada vez

2

Eu gostaria de escrever um programa que leia de um arquivo de texto e imprima em Terminal as palavras daquele caractere de arquivo por caractere a cada um segundo.

Por exemplo, em um arquivo de texto log.txt , digamos que eu tenha esta frase:

I love Unix but I don't know programming.

Eu gostaria que o código lesse a frase anterior e imprimisse as letras, os espaços um por um a cada segundo.

    
por Zahi 08.09.2018 / 22:07

5 respostas

8

A resposta de Goro funcionará, mas deve-se notar que substituição de comando remove novas linhas à direita conforme especificado pelo padrão POSIX . Assim, pode não ser desejável onde você deseja realmente fazer iterações em todos os caracteres, mesmo os não imprimíveis. Outra questão é que o loop de estilo C é usado no bash e no ksh93, mas não no padrão (também conhecido como POSIX-comliant) /bin/sh . A forma ${variable:index:offset} de expansão de parâmetro também é do tipo bashism e não é especificada por POSIX definições de expansão de parâmetro (embora suportadas por ksh93 e zsh ).

No entanto, há uma maneira de iterar todos os caracteres no arquivo de forma portável e de uma forma muito mais prática . Isso é para usar awk :

# all characters on the same line
$ awk '{for(i=1;i<=length;i++){ printf "%c",substr($0,i,1); system("sleep 1");}; print}' input.txt

# all characters on separate lines
$ awk '{for(i=1;i<=length;i++){ print substr($0, i, 1); system("sleep 1"); }}' input.txt

Com este comando, substr() e system() são especificados em POSIX awk e vai, de fato, iterar sobre todos os personagens.

    
por 08.09.2018 / 23:12
3

Você pode fazer isso

var=$(cat log.txt)
for (( i=0; i<${#var}; i++ )); do
 sleep 1 | echo -ne "${var:$i:1}"
done
echo ""
    
por 08.09.2018 / 22:10
3

Com bash ou ksh93 , você pode ler caracteres únicos usando o comando read integrado do shell:

while IFS= read -r -n 1 c; do 
  printf '%c' "$c"
  sleep 1
done < log.txt
printf '\n'
    
por 09.09.2018 / 00:46
1

Aqui está uma solução Python:

python -c "from time import sleep
with open('/tmp/file.txt') as f:
 for line in f:
  for c in line:
   print(c, end='', flush=True);sleep(1);"

Você deve apenas poder colar isso na linha de comando e alterar o nome do arquivo de entrada.

    
por 09.09.2018 / 05:32
0

Você pode fazer isso com Perl , conforme mostrado:

perl -pe 'BEGIN{$/=;$|=1;} sleep 1' log.txt
  • -p irá imprimir automaticamente o registro atual antes de buscar o próximo.
  • $/= fará com que perl leia o fluxo de entrada um byte de cada vez, e assumindo que os caracteres tenham um tamanho de byte.
  • $|=1 será enviado em buffer.
por 09.09.2018 / 21:42