Effetto di $ LANG sul terminale


11

Sto cercando di capire come $LANGsi comporta la variabile con gnome-terminal (e la sua opzione di preferenza per la codifica dei caratteri). Ho usato iso8859-1 (latin1) come set di caratteri principale e tutti i miei nomi di file sono codificati come tali.

Per i seguenti test farò ls -luna directory con caratteri accentati spagnoli nei loro nomi di file:

Caso 1:

  • gnome-terminal configurato per ISO-8859-1
  • LANG impostato su "en_US-iso8859-1"
  • Risultato: vedo tutti i file correttamente

Caso n. 2:

  • gnome-terminal configurato per UTF-8
  • LANG impostato su "en_US-iso8859-1"
  • Risultato: vedo personaggi spazzatura per tutti i personaggi spagnoli. Questo è previsto quando ho cambiato la codifica dei caratteri per il terminale

Caso n. 3:

  • gnome-terminal configurato per ISO-8859-1
  • LANG impostato su "en_US-UTF-8"
  • Risultato: vedo personaggi spazzatura per tutti i personaggi spagnoli.

Perché in questo ultimo caso vedo personaggi confusi? L'output di ls non dovrebbe inviare i nomi dei file direttamente a gnome-terminal così come sono? E poiché gnome-terminal è configurato per ISO-8859-1, mi sarei aspettato che sembrassero giusti.

Per un momento ho pensato che forse bash sta prendendo in considerazione la mia $LANGvariabile e sta eseguendo una conversione. Poi ho cambiato il mio terminale in UTF-8 ma non riesco ancora a vedere i personaggi giusti. Ho persino reindirizzato l'output di ls a xxd e con mia sorpresa vedo ancora i file codificati così come sono: ISO-8859-1.

Per concludere: se il mio elenco contiene caratteri ISO-8859-1 e il mio emulatore di terminale è configurato per la stessa codifica dei caratteri: chi sta facendo la conversione quando LANGè impostato diversamente?

Grazie per tutto l'aiuto che potete fornire.

Craconia

Risposte:


5

L'impostazione per LANGdeve corrispondere a quella del terminale. Più precisamente, l'impostazione per LC_CTYPE(la codifica dei caratteri) deve corrispondere alla codifica del terminale, le altre impostazioni locali non devono corrispondere. E la codifica del terminale è generalmente specificata da un'opzione dell'emulatore di terminale e non da una variabile locale. Le LC_CTYPEcombina due indicazioni: dice applicazioni quali codificano per uso sul terminale (sia per l'input e l'output), e dice applicazioni quali codificano per utilizzare con i file. Nei casi 2 e 3, hai detto lsdi visualizzare l'output in una codifica diversa da quella del terminale, quindi l'output è confuso.

Se lavori con codifiche UTF-8 e latin-1 in momenti diversi, configura il tuo terminale per usare UTF-8. Ciò dovrebbe indurlo a impostare LC_CTYPEun valore che indica UTF-8; non ignorare questa impostazione. (Se l'emulatore di terminale non viene impostato LC_CTYPE, sovrascriverlo nel file di avvio della shell o per l'intera sessione.) Per lavorare con i dati latino-1 in un terminale UTF-8, utilizzare luit(incluso nella suite di utilità X).

LC_CTYPE=en_US.iso88591 luit

(Puoi usare qualsiasi altra locale con la stessa codifica, ad es LC_CTYPE=es_ES.iso88591 luit.)


Grazie Gilles per questa meravigliosa spiegazione, in particolare per aver spiegato le due indicazioni per LC_CTYPE.
Cracovia,

Tornando al mio ultimo caso: ho pensato che, dato che tutti i nomi dei file erano codificati in latino1 oltre al fatto che il mio dispositivo di output finale, quello che creava glifi (il mio terminale) era configurato anche per latino1, mi aspettavo di vedere i file correttamente (indipendentemente da LC_CTYPE) ...
Cracovia,

Non mi è mai venuto in mente di lsprendere in considerazione LC_CTYPE (impostato su UTF-8 in questo caso) e di eseguire una sorta di validazione del set di caratteri: ogni volta che vede qualcosa di non compatibile con il set di caratteri sputa un carattere specifico (ad es. "? "). Ho detto "validazione" perché non eseguirà una "conversione" come fa luit. È così?
Cracovia,

@Craconia Nel terzo caso, lssostituisce i caratteri non stampabili con ?. La maggior parte delle stringhe codificate in latino-1 che rappresentano parole reali hanno caratteri non stampabili se interpretate come UTF-8.
Gilles 'SO- smetti di essere malvagio' il

5

Nel caso # 2 e # 3 stai mescolando due diverse codifiche UTF-8 e Latin-1. Nel caso # 1 stai usando Latin-1 per entrambi, quindi non hai problemi.

Il lscomando (e tutti gli altri programmi ben funzionanti) utilizzano l'impostazione LANG per determinare la codifica .

Puoi mescolare due lingue diverse, ma non dovresti mescolare due diverse codifiche .

Assicurarsi che anche le variabili di ambiente LC_ * utilizzino la stessa codifica della variabile LANG.

Come regola generale, al giorno d'oggi dovresti configurare il tuo sistema per usare solo UTF-8.

Se devi modificare file di dati vecchio stile (es. Proprietà java) dovresti usare un editor specializzato (es. Java ide) o assicurarti la codifica con strumenti come iconvo `ricodificare ..


Grazie. Sì, ho in programma di passare a UTF-8 nel prossimo futuro. Ho un sacco di nomi di file da convertire oltre a molti file di testo. iconv & convmv in soccorso ...
Cracovia,

0

Questo potrebbe essere al di fuori delle tue necessità, ma ...

Si scopre in RHEL5, e probabilmente prima, molte delle pagine man sono state in qualche modo asciugate per qualche motivo abbandonato. Cioè, la pagina man grezza è stata convertita dal suo set di caratteri nativi in ​​ASCII a 7 bit. Indipendentemente da ciò che fai con LC e LANG, la pagina man per latin1produce una pagina man che è effettivamente inutile. Tutti i caratteri speciali (8 bit) all'interno sono stati sostituiti con segnaposto a 7 bit (in genere ??). Lo trovo divertente.

Ma la utf8versione di queste pagine man potrebbe esistere nella directory specifica della lingua. Il trucco è chiedere loro con il loro giusto nome. Ad esempio, latin1 è in realtà iso_8859-1. Se fai una pagina man su di essa e le tue impostazioni LANG sono corrette, vedi cosa ti aspetti; la pagina man si trova nel subdir specifico della lingua ( en/man7/iso_8859-1.7). Ma se chiedi iso-8859-1, per qualche motivo, ottieni la versione ASCII.

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.