Newsgroup: it.comp.lang.c++
Titolo: ANSI vs UNICODE. Cosa fa lo standard? (lunghetto)

Salve a tutti. Postai tempo addietro un quesito analogo ma la domanda era
mal posta. Riprovo:
Sappiamo tutti che esistono 2 modi che vanno per la maggiore per gestire i
dati di tipo "testuale" (diciamo pure le stringhe):
1-  ANSI -> 1 carattere == 1 byte == 1 char
2 - UNICODE -> 1 carattere == 2bytes == 1 wchar_t
Ai vecchi tempi, il mondo dei computer parlava una sola lingua, e la
codifica ANSI andava benissimo.
Oggi non è più vero, ma ho l'impressione che lo standard c++ sia rimasto un
pelo indietro.
Premetto che il mio background è WIN+MFC. Su questa piattaforma il problema
è stato affrontato (secondo me bene) alla radice: hanno creato tipi
"mutanti" a seconda della compilazione (TCHAR e compagnia bella), e invitano
il programmatore ad usare SOLO quelli. Nello stesso tempo tutta la libreria
(MFC e API WIN32) è perfettamente coerente con questo approccio.
Siccome però mi capita sempre più spesso di scrivere moduli con interfaccia
console, magari con un occhio alla portabilità, cerco sempre più di
utilizzare C++ standard.
Ma resta (per me) irrisolto il problema di fondo:
io vorrei un sorgente "scritto bene", in grado di compilare sia ANSI che
UNICODE per almeno 2 motivi:
1 - internazionalizzazione
2 - performance su sistemi nativamente UNICODE (che ormai credo siano la
maggioranza).
A questo punto ecco le mie domande (o spunti di riflessione)
A - Possibile che lo standard faccia finta di niente o quasi ?
B - Devo arrangiarmi e definire il mio "castello" fatto di TCHAR ecc... ?
C - Per la mia documentazione, la libreria standard C definisce puntualmente
le varianti _t*
Ad Es. _tcslen (generica), strlen (ansi), wcslen (UNICODE)
E' una caratteristica standard o un estensione del mio compilatore/ambiente
(microsoft) ?
D - Ok, è vero in STL hanno fatto un buon lavoro con basic_string, string e
wstring, ma ho l'impressione che i progettisti si siano fatti sfuggire
qualche dettaglio.
Un esempio per tutti (ma che mi mette in grossa difficoltà): il costruttore
di basic_ifstream.
Ma per quale maledetto motivo vuole un const char * per passargli il nome
del file????
E io cosa gli passo in un sistema interamente unicode ???
Ho il sospetto che la cosa funzioni così: il mio nome di file è UNICODE, lo
converto in ANSI per passarlo a basic_ifstream() che internamente lo
riconverte in UNICODE per chiamare l'API nativa del S.O. E' così ?
Se fosse così, significa che lo standard c++ "preferisce" ambienti ANSI (che
credo stiano praticamente scomparendo).
E - Ma voi (vedo che tra i frequentatori dell'N.G. che ci sono alcune
persone davvero molto esperte) come affrontate questo problema? o ritenete
che non sia un problema?
Ciao e grazie per l'attenzione
Beppe

 che non sia un problema?
Usando librerie proprietarie, che altro si puo' fare?
Ciao,
Nicola

Nicola
Ciao e grazie
Beppe

 E io cosa gli passo in un sistema interamente unicode ???
Che poi mi sono dimenticato la cosa più importante:
E SE NEL NOME DEL FILE CI SONO CARATTERI NON ANSI????????
Tale file non può essere aperto da STL????
Questo sarebbe un limite gravissimo.
Ciao
Beppe

L'idea e' che i fornitori di compilatori e librerie introducano degli
overload specifici per le piattaforme che supportano, ma questo non
credo sia mai successo.
Ciao,
Nicola

 credo stiano praticamente scomparendo).
Attenzione a non confondere l'uso di 'const char*' con l'idea che i nomi 
di file debbano essere limitati al basic character set di 96 caratteri: 
è la piattaforma che definisce il significato dell'argomento, e può 
farlo ad esempio scegliendo una codifica multibyte. Esiste un'ampia 
gamma di casi in cui è sufficiente (ed efficiente) *non fare nulla*, 
ovvero trattare la sequenza di 'char' come *il* nome del file senza 
porsi tanti problemi su che caratteri vi compaiano e in che lingua 
siano: ad esempio, quando si traffica con dei file temporanei, quando si 
apre un file ottenuto da un dialogo e così via.
Esistono casi in cui questo approccio non è adeguato, ad esempio quando 
dato un nome di file "prova" si vuole creare un file denominato 'copia 
di prova': ma giustamente in tali casi ci vuole ben altra infrastruttura 
che fstream(const wchar_t *).
Barone Frankenstein
-- 
Paranoia is an afterthought.