Come convertire i file txt UTF-8 in maiuscolo in bash?


10

Ho alcuni file .txt UTF-8 che vorrei convertire in maiuscolo. Se fosse solo ASCII, potrei usare:

tr [:lower:] [:upper:]

Ma dal momento che sto lavorando con i segni diacritici e roba del genere, non sembra funzionare. Immagino che potrebbe funzionare se imposto le impostazioni internazionali appropriate, ma ho bisogno che questo script sia portatile.

Risposte:


14

Tutto di:

tr '[:lower:]' '[:upper:]'

(non dimenticare le virgolette, altrimenti che non funziona se c'è un file chiamato :, l, ... o rnella directory corrente) oppure:

awk '{print toupper($0)}'

o:

dd conv=ucase

hanno lo scopo di convertire i caratteri in maiuscolo in base alle regole definite nella locale corrente. Tuttavia, anche laddove le versioni locali utilizzano UTF-8 come set di caratteri e definiscono chiaramente la conversione da lettere minuscole a maiuscole, almeno GNU dd, GNU tre mawk(l'impostazione predefinita awksu Ubuntu per esempio) non li seguono. Inoltre, non esiste un modo standard per specificare locali diversi da Co POSIX, quindi se si desidera convertire i file UTF-8 in maiuscolo in modo portabile indipendentemente dalle impostazioni internazionali correnti, si è sfortunati con il toolchest standard.

Come spesso, per portabilità, la tua scommessa migliore potrebbe essere perl:

$ echo lľsšcčtťzž | PERLIO=:utf8 perl -pe '$_=uc'
LĽSŠCČTŤZŽ

Ora, devi stare attento che non tutti sono d'accordo su quale sia la versione maiuscola di un personaggio specifico.

Ad esempio, nelle versioni locali turche, inon è maiuscolo I, ma İ( <U0130>). Qui con il toolchest cimelio trinvece di GNU tr:

$ echo ií | LC_ALL=C.UTF-8 tr '[:lower:]' '[:upper:]'
IÍ
$ echo ií | LC_ALL=tr_TR.UTF-8 tr '[:lower:]' '[:upper:]'
İÍ

Sul mio sistema, la perlconversione in alto è definita in /usr/share/perl/5.14/unicore/To/Upper.pl, e trovo che si comporti in modo diverso su alcuni caratteri della libc GNU toupper()nelle impostazioni C.UTF8locali per esempio, perlessendo più accurato. Ad esempio, perlconverte correttamente ɀ in Ɀ , la GNU libc (2.17) no.


Per quello che vale, sto lavorando con lettere ceche (e l'esempio che hai usato è in realtà slovacco), dove tutte le lettere maiuscole sono chiaramente definite, ma il set di impostazioni locali sarà probabilmente C e non ceco, quindi questo è un problema. Perl è già utilizzato in questa toolchain, quindi aggiungere un altro uso potrebbe non essere così male. Grazie per la spiegazione dettagliata, a proposito!
VPeric,

3

Penso che puoi farlo con awke la sua toupperfunzione.

Per esempio

Non funziona con GNU tr:

$ echo lľsšcčtťzž | tr '[:lower:]' '[:upper:]'
LľSšCčTťZž

Funziona con GNU awk:

$ echo lľsšcčtťzž | awk '{ print toupper($0) }'
LĽSŠCČTŤZŽ

@StephaneChazelas - grazie ho cambiato l'esempio fallito.
slm

Dipende dalle impostazioni internazionali correnti e dall'implementazione tro awk. Ad esempio, la maggior parte trconvertirà correttamente il carattere quando si trova in una locale UTF8, secondo la locale corrente, GNU trno. mawknon lo fa.
Stéphane Chazelas,

1
In realtà, su FreeBSD (9.1), è il contrario. Funziona con tr, ma non conawk
Stéphane Chazelas, il

@StephaneChazelas - Non sono esperto delle variazioni Cool. Qualcuno ha appena votato, chiedo perché?
slm

2

Funziona con OS X trma non con GNU tr:

tr '[:lower:]' '[:upper:]'

Funziona con gawkma non con mawko nawk(che si trova /usr/bin/awkin OS X):

awk '{print toupper($0)}'

Un'altra opzione è usare GNU sed:

sed 's/./\u&/g'

In Bash 4.0 e versioni successive puoi anche utilizzare l' ^^espansione dei parametri:

while IFS= read -r l;do printf %s\\n "${l^^}";done
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.