Reverte todas as palavras na linha atual

2

Eu tenho um arquivo e quero reverter todas as palavras nele.

ex file de entrada:

DCBA. HGFE.GI
MLK,PON.RQ
UTS. ZYXWV. 321

arquivo de saída ex: ( O que eu quero )

ABCD. EFGH.IG
KLM,NOP.QR
STU. VWXYZ. 123

Com este script sed: sed '/\n/!G;s/\(.\)\(.*\n\)/&/;//D;s/.//' toda a linha inteira é invertida.

A saída errada produzida pelo comando acima:

IG.EFGH .ABCD    
QR.NOP,KLM    
123 .VWXYZ .STU 

Como posso obter o resultado desejado?

    
por αғsнιη 22.08.2014 / 16:30

3 respostas

7

Experimente este em pura bash

#!/bin/bash
while IFS= read -N1 char; do
    if [[ "$char" =~ [[:alnum:]] ]]; then
        word="$char$word"
    else
        echo -n "$word$char"
        word=""
    fi
done <input.file >output.file

Saída:

ABCD. EFGH.IG
KLM,NOP.QR
STU. VWXYZ. 123

Essa lógica de código é bem simples. Nós lemos o caractere de arquivo por caractere (graças ao -N1 flag. O IFS= é necessário para poder ler as novas linhas também), então adicionamos cada caractere válido que encontramos no início da variável $word ( invertendo assim a palavra). Quando encontramos um caractere não alfanumérico, fazemos eco do valor de $word e redefinimos o valor para vazio. Repetimos esses passos até o final do arquivo

    
por Aserre 22.08.2014 / 17:28
4

Então, você realmente quer reverter cada palavra , não cada sentença, certo? Ou a sua vírgula deveria ser um período?

perl -pe 's/(\w+)/ reverse  /eg' << END
DCBA. HGFE.GI
MLK,PON.RQ
UTS. ZYXWV. 321
END
ABCD. EFGH.IG
KLM,NOP.QR
STU. VWXYZ. 123

Se você quiser redirecionar, faça o seguinte:

perl -pe 's/(\w+)($|\W+)/ reverse() .  /eg' < file_in > file_out

Com o meu exemplo, faça

perl -pe 's/(\w+)($|\W+)/ reverse() .  /eg' << END > file_out

NÃO coloque o redirecionamento na mesma linha que a palavra final do heredoc. Se você fizer isso, o shell não será capaz de encontrar o fim do heredoc.

Com o redirecionamento de e para arquivos, nunca faça isso: command < file > file com o mesmo arquivo. Os redirecionamentos acontecem antes do início do comando e > truncará o arquivo para comprimento zero. Quando o comando inicia, o arquivo de entrada já foi destruído.

    
por glenn jackman 22.08.2014 / 17:34
1

E a opção detalhada (python):

#!/usr/bin/env python3

with open("/path/to/sourcefile") as messed_up:
    lines = [list(line.replace("\n", "")) for line in messed_up]

def reverse_line(l):
    i=0; line = ""; sep = (" ", ",",".")
    while i < len(l):
        word = []
        while not l[i] in sep:
            word.append(l[i]); i = i+1
            if i == len(l):
                line = line + ("").join(reversed(word)); break
        else:
            line = line + ("").join(reversed(word)) + l[i]
        i = i+1
    print(line)

for l in lines:
    reverse_line(l)

Saídas:

ABCD. EFGH.IG
KLM,NOP.QR
STU. VWXYZ. 123

As linhas são "construídas" da esquerda para a direita; caracteres na lista sep (espaços, vírgulas, pontos ou qualquer outro definido) e outros caracteres únicos são colocados diretamente na linha, um número consecutivo de outros caracteres são coletados primeiro e revertidos antes de serem adicionados à linha. / p>     

por Jacob Vlijm 22.08.2014 / 22:45