Esiste un'alternativa a sed che supporta Unicode?


33

Per esempio:

sed 's/\u0091//g' file1

In questo momento, devo fare hexdumpper ottenere il numero esadecimale e inserire sedcome segue:

$ echo -ne '\u9991' | hexdump -C
00000000  e9 a6 91                                          |...|
00000003

E poi:

$ sed 's/\xe9\xa6\x91//g' file1

Risposte:


28

Basta usare quella sintassi:

sed 's/馑//g' file1

O nella forma di escape:

sed "s/$(echo -ne '\u9991')//g" file1

(Nota che le versioni precedenti di Bash e alcune shell non capiscono echo -e '\u9991', quindi controlla prima.)


1
Sed conta 馑 come un personaggio o 3? Cioè, echo 馑 | sed s/...//stampa qualcosa?
user253751

@immibis Poiché sedha il modificatore g, sostituisce tutte le occorrenze anche quando si susseguono. Anche sed dovrebbe contarlo come un personaggio, vedi: echo -ne "馑" | wc -m1. Se si contano i byte ( wc -c) ritornerebbe 3. Ho capito bene la tua domanda?
caos,

Intendevo: .significa "un carattere" o "un byte"?
user253751

@immibis I corrisponde a un personaggio quindi echo 馑 | sed s/...//mi dà (niente viene sostituito)
caos

4
@chaos: funziona sotto en_US.UTF-8, ma non sotto C.
Choroba,

15

Perl può farlo:

echo 汉典“馑”字的基本解释 | perl -CS -pe 's/\N{U+9991}/Jin/g'

-CS attiva UTF-8 per input, output ed errori standard.


7
Perl può fare quasi tutto .....
wobbily_col,

6

Diverse versioni del sedsupporto Unicode :

  • Heirloom sed , che si basa sul "materiale Unix originale".
  • GNU sed , che è la sua base di codice.
  • Plan 9 sed , che è stato portato su sistemi operativi simili a Unix.

Non sono riuscito a trovare informazioni su BSD sed, che ho pensato fosse strano, ma penso che le probabilità siano buone che supporti anche Unicode. Sfortunatamente, non esiste un modo standard per dire sedquale codifica usare, quindi ognuno lo fa a modo suo.


Supportano UTF-16 con e senza DBA?
Bon Ami,

10
UTF-16 è piuttosto inutilizzabile nei sistemi operativi basati su Unix. È anche un abominio che non avrebbe mai dovuto vedere la luce del giorno.
Brian Bi,

Il fatto che supportino o meno UTF-16 dipende dall'implementazione e temo di non disporre di tali dati. Dubito che Plan 9 sed lo faccia (il sistema operativo originale è UTF-8 ovunque), ma non posso esserne sicuro, e anche se non lo fosse, gli altri potrebbero.
The Spooniest

2

Questo funziona per me:

$ vim -nEs +'%s/\%u9991//g' +wq file1

È una goccia più prolissa di quanto vorrei; ecco una spiegazione completa:

  • -n disabilita il file di scambio vim
  • -E Ex modalità migliorata
  • -s modalità silenziosa
  • +'%s/\%u9991//g' eseguire il comando di sostituzione
  • +wq salva ed esci

Suppongo che questo modifichi file1 sul posto , è corretto?
Gerrit,

@gerrit è corretto, e grazie per averlo sottolineato.
Aryeh Leib Taurog,

1

Con le versioni recenti di BASH, ometti le virgolette intorno all'espressione sed e puoi usare le stringhe con escape di BASH. Gli spazi all'interno dell'espressione sed o parti dell'espressione sed che potrebbero essere interpretati da BASH come caratteri jolly possono essere citati individualmente.

$ echo "饥馑荐臻" | sed s/$'\u9991'//g
饥荐臻

Questa dovrebbe essere la nuova risposta accettata, semplice e pulita!
Allen Wang,

0

Funziona per me con GNU sed (versione 4.2.1):

$ echo -ne $'\u9991' | sed 's/\xe9\xa6\x91//g' | hexdump -C
$ echo -ne $'\u9991' | hexdump -C
00000000  e9 a6 91

(Come altro sostituto per sedte potresti anche usare GNU awk; ma non sembra necessario.)

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.